Advertisement
Guest User

Untitled

a guest
Oct 22nd, 2019
107
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.05 KB | None | 0 0
  1. /*
  2. create table vc(matricula varchar(8), nr_idcivil int, data_inicio date, data_fim date);
  3. */
  4.  
  5. delete from vc;
  6. insert into vc values('AA-BB-11', 1234, to_date('2019-10-01', 'yyyy-mm-dd'), null);
  7. insert into vc values('AA-BB-11', 5678, to_date('2019-10-04', 'yyyy-mm-dd'), to_date('2019-10-08', 'yyyy-mm-dd'));
  8. insert into vc values('AA-BB-11', 9012, to_date('2019-10-06', 'yyyy-mm-dd'), to_date('2019-10-09', 'yyyy-mm-dd'));
  9. insert into vc values('CC-DD-11', 1234, to_date('2019-10-08', 'yyyy-mm-dd'), to_date('2019-10-14', 'yyyy-mm-dd'));
  10. insert into vc values('AA-BB-11', 1234, to_date('2019-10-10', 'yyyy-mm-dd'), null);
  11. insert into vc values('EE-FF-11', 1234, to_date('2019-10-18', 'yyyy-mm-dd'), null);
  12. --insert into vc values('GG-HH-11', 1234, to_date('2019-10-01', 'yyyy-mm-dd'), null);
  13. commit;
  14.  
  15. /*
  16. Escreva uma função que devolva um valor booleano indicando se existem sobreposições temporais nas associações de veículos a condutores.
  17. */
  18.  
  19. create or replace function fnc_existem_sobreposicoes return boolean
  20. as
  21. v_count int;
  22. begin
  23. select count(*) into v_count
  24. from (select *
  25. from vc a, vc b
  26. where (a.matricula != b.matricula or a.nr_idcivil != b.nr_idcivil or a.data_inicio != b.data_inicio)
  27. and a.matricula = b.matricula
  28. and a.data_inicio >= b.data_inicio and (a.data_inicio < b.data_fim or b.data_fim is null)
  29. union
  30. select *
  31. from vc a, vc b
  32. where (a.matricula != b.matricula or a.nr_idcivil != b.nr_idcivil or a.data_inicio != b.data_inicio)
  33. and a.nr_idcivil = b.nr_idcivil
  34. and a.data_inicio >= b.data_inicio and (a.data_inicio < b.data_fim or b.data_fim is null));
  35. return v_count > 0;
  36. end;
  37. /
  38.  
  39. declare
  40. v_flag boolean;
  41. begin
  42. v_flag := fnc_verificar_sobreposicoes;
  43. if v_flag then
  44. dbms_output.put_line('Existem sobreposições');
  45. else
  46. dbms_output.put_line('Não existem sobreposições');
  47. end if;
  48. end;
  49. /
  50.  
  51. /*
  52. Escreva um procedimento que detete, e corrija, as associações de condutores a veículos que se sobrepôem temporalmente.
  53. Considere que os atributos data_inicio e data_fim são datas, e que os intervalos são fechados na data de início e abertos na data de fim.
  54. A correção consiste em analisar as sobreposições, por matrícula e por condutor, e deve seguir a seguinte lógica:
  55. a) Processar matrículas, e para cada registo que tenha de ser modificado, colocar a data de fim igual à data inicial do período seguinte.
  56. b) Processar condutores, e para cada registo que tenha de ser modificado, colocar a data de fim igual à data inicial do período seguinte.
  57. c) Se após o processamento não tiver sido possível corrigir todas as sobreposições, então deve abortar o processamento gerando uma exceção.
  58. */
  59.  
  60. create or replace procedure prc_corrigir_associacoes
  61. as
  62. cursor c1 is
  63. select *
  64. from vc
  65. order by matricula, data_inicio
  66. for update of data_fim;
  67. cursor c2 is
  68. select *
  69. from vc
  70. order by nr_idcivil, data_inicio
  71. for update of data_fim;
  72. v_data date;
  73. v_flag boolean;
  74. ex_sobreposicoes exception;
  75. begin
  76. for r in c1 loop
  77. select min(data_inicio) into v_data
  78. from vc
  79. where matricula = r.matricula
  80. and data_inicio > r.data_inicio;
  81. if (v_data is not null) and (v_data < r.data_fim or r.data_fim is null) then
  82. update vc
  83. set data_fim = v_data
  84. where current of c1;
  85. end if;
  86. end loop;
  87. for r in c2 loop
  88. select min(data_inicio) into v_data
  89. from vc
  90. where nr_idcivil = r.nr_idcivil
  91. and data_inicio > r.data_inicio;
  92. if (v_data is not null) and (v_data < r.data_fim or r.data_fim is null) then
  93. update vc
  94. set data_fim = v_data
  95. where current of c2;
  96. end if;
  97. end loop;
  98. if fnc_existem_sobreposicoes then
  99. raise ex_sobreposicoes;
  100. end if;
  101. exception
  102. when ex_sobreposicoes then
  103. raise_application_error(-20000, 'Existem sobreposições');
  104. end;
  105. /
  106.  
  107. begin
  108. prc_corrigir_associacoes;
  109. end;
  110. /
  111. select * from vc order by data_inicio;
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement