Dúvida Cursor

Dúvidas, dicas e truques de PL/SQL. Aqui também vão assuntos relacionados a pacotes, triggers, funções, Java-Stored Procedures, etc
Responder
Ivone
Rank: Programador Júnior
Rank: Programador Júnior
Mensagens: 16
Registrado em: Sex, 05 Mar 2010 1:13 pm
Localização: São Paulo
Ivone

Pessoal, estou precisando de ajuda para montar um cursor, está dando erro no sinal de + e não sei como fazer a soma

Segue código:

Selecionar tudo

DECLARE
CURSOR REGISTRO
Is
	SELECT FV.CODFUNC, FV.PLACA_VEIC, V.ANO_FABRI
	FROM FUNC_VEIC FV, VEICULO V
	WHERE V.PLACA = FV.PLACA_VEIC
	AND FV.DATA_FIM_USO IS NULL
	FOR UPDATE;
BEGIN
	FOR REG_VEICULO IN REGISTRO
	LOOP
		IF (REG_VEICULO.ANO_FABRI < 1990) THEN
			UPDATE FUNC_VEIC SET DATA_FIM_USO = '31/12/2007';
		
		IF (REG_VEICULO.ANO_FABRI BETWEEN 1990 AND 2000) THEN
			UPDATE FUNC_VEIC SET DATA_FIM_USO = REG_VEICULO.ANO_FABRI + 15;
		
		IF(REG_VEICULO.ANO_FABRI > 2000) THEN
			UPDATE FUNC_VEIC SET DATA_FIM_USO = REG_VEICULO.ANO_FABRI + 20;
	END IF;
	END IF;
	END IF;
	END LOOP;

END;
/
Obrigada
gfkauer
Rank: DBA Sênior
Rank: DBA Sênior
Mensagens: 389
Registrado em: Ter, 27 Jul 2010 1:34 pm
Localização: Sapiranga - RS
Contato:
Quem falou que programar era fácil??

Quanto mais dificil for a implementação mais valorizado seu trabalho será!

Acessem: www.gfkauer.com.br

Ivone,
A coluna ano_fabric da tabela Veiculo é numérica?

Poderia dar um desc das tabelas e postar aqui para ser avaliado?
Ivone
Rank: Programador Júnior
Rank: Programador Júnior
Mensagens: 16
Registrado em: Sex, 05 Mar 2010 1:13 pm
Localização: São Paulo
Ivone

Sim o campo ANO_ABRI é numérico

Segue dados das tabelas

Selecionar tudo

CODVEICULO    PLACA	ANO_FABRI        COD_TIPO
1	        WVX9876	2009	         FIESTA
2	        BKQ3254	2005	         CORSA
3	        WXY4574	1989	         FORD KA
4	        PKB4521	1991	         CAMINHAO

PLACA_VEIC  CODFUNC  DATA_INICIO_USO  DATA_FIM_USO
BXD4567	     111	     12/7/2010	   12/7/2020
PKB4521	     112	     8/5/2009	   12/7/2020
PBW3487	     113	     2/3/2005	   2/3/2015
WXY4574	     111	     2/3/2005	
BKQ3254	     112	     2/3/2005	
WVX9876	     113	     7/9/2009
Não sei se é isso que você precisa

Obrigada
SergioLBJr
Rank: Oracle Guru
Rank: Oracle Guru
Mensagens: 448
Registrado em: Ter, 16 Jun 2009 3:07 pm
Localização: Parobé - RS
Sérgio Luiz Bonemberger Junior
Programador Junior
Parobé RS

[]s

Cara o que lhe tinha sido pedido era a descrição dos campos da tabela.
Quais campos são number, quais são date, por ai vai...

Mas pelo que vi o problema é que tu ta jogando valores numéricos para um campo de data.

específicamente nessas linhas.

Selecionar tudo

IF (REG_VEICULO.ANO_FABRI BETWEEN 1990 AND 2000) THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = REG_VEICULO.ANO_FABRI + 15; 
       
      IF(REG_VEICULO.ANO_FABRI > 2000) THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = REG_VEICULO.ANO_FABRI + 20;
Se o campo data_fim_uso for do tipo date vai dar problema de conversão de dados.

O que você deseja jogar nele? O primeiro dia do ano de fabricação??

E quando você soma + 15 no ano de fabricação seriam mais 15 anos ??

Especifica um pouco mais a sua dúvida que conseguiremos a solução.

O que tu
Ivone
Rank: Programador Júnior
Rank: Programador Júnior
Mensagens: 16
Registrado em: Sex, 05 Mar 2010 1:13 pm
Localização: São Paulo
Ivone

Oi Sérgio,
Então, o campo ANO_FABRI é numérico e o campo DATA_FIM_USO é date
Agora entendi o problema...enfim eu gostaria de fazer o seguinte, verificar se o ano de fabricação está entre 1990 e 2000, se sim acrescentar 15 anos e se for maior q 2000, acrescentar 20 anos para o campo DATA_FIM_USO, mas acho que devou usar de alguma maneira o campo DATA_INICIO_USO para pegar o dia e mês.
Sei que tem uma função (MONTHS), mas não sei usar, tem como eu usar o campo ANO_FABRI como campo date e passar apenas o ano de fabricação?
Segue as tabelas:

Selecionar tudo

CREATE TABLE FUNC_VEIC(
PLACA_VEIC VARCHAR2(7) PRIMARY KEY, 
CODFUNC REFERENCES FUNC,
DATA_INICIO_USO DATE,
DATA_FIM_USO DATE
);

CREATE TABLE VEICULO(
CODVEICULO NUMBER(3) PRIMARY KEY,
PLACA VARCHAR2(7) REFERENCES FUNC_VEIC,
ANO_FABRI NUMBER(4),
COD_TIPO REFERENCES TIPO_VEICULO
);
Obrigada
SergioLBJr
Rank: Oracle Guru
Rank: Oracle Guru
Mensagens: 448
Registrado em: Ter, 16 Jun 2009 3:07 pm
Localização: Parobé - RS
Sérgio Luiz Bonemberger Junior
Programador Junior
Parobé RS

[]s

Tenta aí.

Selecionar tudo

DECLARE 
CURSOR REGISTRO 
Is 
   SELECT FV.CODFUNC, FV.PLACA_VEIC, V.ANO_FABRI 
   FROM FUNC_VEIC FV, VEICULO V 
   WHERE V.PLACA = FV.PLACA_VEIC 
   AND FV.DATA_FIM_USO IS NULL 
   FOR UPDATE; 
BEGIN 
   FOR REG_VEICULO IN REGISTRO 
   LOOP 
      IF (REG_VEICULO.ANO_FABRI < 1990) THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = '31/12/2007'; 
       
      IF (REG_VEICULO.ANO_FABRI BETWEEN 1990 AND 2000) THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = ADD_MONTHS(DATA_FIM_USO,(REG_VEICULO.ANO_FABRI + 15) *12); 
       
      IF(REG_VEICULO.ANO_FABRI > 2000) THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = ADD_MONTHS(DATA_FIM_USO,(REG_VEICULO.ANO_FABRI + 20)*12); 
   END IF; 
   END IF; 
   END IF; 
   END LOOP; 

END;
Ivone
Rank: Programador Júnior
Rank: Programador Júnior
Mensagens: 16
Registrado em: Sex, 05 Mar 2010 1:13 pm
Localização: São Paulo
Ivone

Sérgio,
Atualizou todos os campos com a data 31/12/2007. estou tentando a Solução, é realmente não é fácil programar, mas é muito legal
Assim que eu tiver a solução, posto novamente
Obrigada pela ajuda
diegopedrao
Rank: Analista Sênior
Rank: Analista Sênior
Mensagens: 164
Registrado em: Sex, 22 Ago 2008 12:28 pm
Localização: SP

Selecionar tudo


DECLARE 
CURSOR REGISTRO 
Is 
   SELECT FV.ROWID, FV.CODFUNC, FV.PLACA_VEIC, V.ANO_FABRI 
   FROM FUNC_VEIC FV, VEICULO V 
   WHERE V.PLACA = FV.PLACA_VEIC 
   AND FV.DATA_FIM_USO IS NULL 
   FOR UPDATE; 
BEGIN 
   FOR REG_VEICULO IN REGISTRO 
   LOOP 
      IF (REG_VEICULO.ANO_FABRI < 1990) THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = '31/12/2007'
          WHERE ROWID = REG_VEICULO.ROWID;

      IF (REG_VEICULO.ANO_FABRI BETWEEN 1990 AND 2000) THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = ADD_MONTHS(DATA_FIM_USO,(REG_VEICULO.ANO_FABRI + 15) *12)
          WHERE ROWID = REG_VEICULO.ROWID; 
        
      IF(REG_VEICULO.ANO_FABRI > 2000) THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = ADD_MONTHS(DATA_FIM_USO,(REG_VEICULO.ANO_FABRI + 20)*12)
            WHERE ROWID = REG_VEICULO.ROWID;

   END IF; 
   END IF; 
   END IF; 
   END LOOP; 

END;
Tenta assim ;)

Att,

Diego Monteiro
SergioLBJr
Rank: Oracle Guru
Rank: Oracle Guru
Mensagens: 448
Registrado em: Ter, 16 Jun 2009 3:07 pm
Localização: Parobé - RS
Sérgio Luiz Bonemberger Junior
Programador Junior
Parobé RS

[]s

Ééé, não percebi a falta dos where nos updates.

quanto a programar nem te stressa pl-sql é rapidinho pra começar a pegar as manhas.

Vai ficando bem mais fácil dpoiz de alguns meses.
Ivone
Rank: Programador Júnior
Rank: Programador Júnior
Mensagens: 16
Registrado em: Sex, 05 Mar 2010 1:13 pm
Localização: São Paulo
Ivone

Pessoal, o cursor com data ainda precisa de alguns ajuste na hora de calcular os dias, mas enfim, este outro cursor compilou com sucesso, mas não insere nada na tabela Teste.

Selecionar tudo

CREATE OR REPLACE PROCEDURE INSERT_FUNCIONARIO(
P_CODFUNCIONARIO IN FUNCIONARIO.CODFUNCIONARIO%TYPE,
P_NOMEFUNCIONARIO IN FUNCIONARIO.NOMEFUNCIONARIO%TYPE,
P_DATANASCIMENTO IN FUNCIONARIO.DATANASCIMENTO%TYPE,
P_SEXO IN FUNCIONARIO.SEXO%TYPE)
IS

CURSOR TESTE_IVONE
IS
 SELECT F.CODFUNCIONARIO CODIGO,
        F.NOMEFUNCIONARIO NOME,
        F.DATANASCIMENTO DATA_NASC,
        F.SEXO SEXO
        FROM FUNCIONARIO F, ENDERECOFUNC EF
        WHERE F.CODFUNCIONARIO = P_CODFUNCIONARIO
        AND   F.CODFUNCIONARIO = EF.CODFUNCIONARIO
        AND   F.DATANASCIMENTO >= '01/01/1973';
VCODIGO FUNCIONARIO.CODFUNCIONARIO%TYPE;
VNOME FUNCIONARIO.NOMEFUNCIONARIO%TYPE;
VDATANASCIMENTO FUNCIONARIO.DATANASCIMENTO%TYPE;
VSEXO FUNCIONARIO.SEXO%TYPE;
 
BEGIN
  FOR REG_FUNCIONARIO  IN TESTE_IVONE
  LOOP
  INSERT INTO TESTE  
  VALUES(VCODIGO, VNOME, VDATANASCIMENTO, VSEXO);
  END LOOP;

END;
SergioLBJr
Rank: Oracle Guru
Rank: Oracle Guru
Mensagens: 448
Registrado em: Ter, 16 Jun 2009 3:07 pm
Localização: Parobé - RS
Sérgio Luiz Bonemberger Junior
Programador Junior
Parobé RS

[]s

Por via de dúvidas execute o select do cursor pra ver se esta retornando o que tu desejas.

Mas ta faltando um commit aí pra gravar as inserções de vez.
Ivone
Rank: Programador Júnior
Rank: Programador Júnior
Mensagens: 16
Registrado em: Sex, 05 Mar 2010 1:13 pm
Localização: São Paulo
Ivone

O select retorna valores sim e mesmo colocando o commit ele não insere.
gfkauer
Rank: DBA Sênior
Rank: DBA Sênior
Mensagens: 389
Registrado em: Ter, 27 Jul 2010 1:34 pm
Localização: Sapiranga - RS
Contato:
Quem falou que programar era fácil??

Quanto mais dificil for a implementação mais valorizado seu trabalho será!

Acessem: www.gfkauer.com.br

Creio que identifiquei o erro.
você esta inserindo com base nas variaveis que criou, mas em momento algum as alimenta...

tente algo assim:

Selecionar tudo

Create Or Replace Procedure insert_funcionario(p_codfuncionario  In funcionario.codfuncionario%Type,
                                               p_nomefuncionario In funcionario.nomefuncionario%Type,
                                               p_datanascimento  In funcionario.datanascimento%Type,
                                               p_sexo            In funcionario.sexo%Type) Is

  Cursor teste_ivone Is
    Select f.codfuncionario  codigo,
           f.nomefuncionario nome,
           f.datanascimento  data_nasc,
           f.sexo            sexo
      From funcionario  f,
           enderecofunc ef
     Where f.codfuncionario = p_codfuncionario
       And f.codfuncionario = ef.codfuncionario
       And f.datanascimento >= '01/01/1973';
  v_cur teste_ivone%Rowtype;

Begin
  Open teste_ivone Loop Fetch teste_ivone
    Into v_cur;
  Exit When teste_ivon%Notfound;
  Insert Into teste
  Values
    (v_cur.codigo,
     v_cur.nome,
     v_cur.data_nasc,
     v_cur.sexo);
End Loop;

End;
Creio que obtera resultado agora...
SergioLBJr
Rank: Oracle Guru
Rank: Oracle Guru
Mensagens: 448
Registrado em: Ter, 16 Jun 2009 3:07 pm
Localização: Parobé - RS
Sérgio Luiz Bonemberger Junior
Programador Junior
Parobé RS

[]s

coloca um exceptio no seu begin com um dbms_output.putline(SQLERRM);

deve ta dando pau na hora do insert.
Ivone
Rank: Programador Júnior
Rank: Programador Júnior
Mensagens: 16
Registrado em: Sex, 05 Mar 2010 1:13 pm
Localização: São Paulo
Ivone

Pessoal,
Consegui finalizar o Cursor de Data mas ainda falata o Cursor de Insert, ele ficou assim:

Selecionar tudo

DECLARE 
CURSOR REGISTRO 
Is 
   SELECT FV.ROWID, FV.CODFUNC, FV.PLACA_VEIC, V.ANO_FABRI 
   FROM FUNC_VEIC FV, VEICULO V 
   WHERE V.PLACA = FV.PLACA_VEIC 
   AND FV.DATA_FIM_USO IS NULL 
   FOR UPDATE; 
BEGIN 
   FOR REG_VEICULO IN REGISTRO 
   LOOP 
      IF EXTRACT(YEAR FROM REG_VEICULO.ANO_FABRI) < ('1990') THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = '31/12/2007' 
          WHERE ROWID = REG_VEICULO.ROWID; 
      END IF; 

      IF EXTRACT(YEAR FROM REG_VEICULO.ANO_FABRI) BETWEEN '1990' AND '2000' THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = ADD_MONTHS(REG_VEICULO.ANO_FABRI, 180)         
          WHERE ROWID = REG_VEICULO.ROWID;    
      END IF;
   
      IF EXTRACT(YEAR FROM REG_VEICULO.ANO_FABRI) > ('2000') THEN 
         UPDATE FUNC_VEIC SET DATA_FIM_USO = ADD_MONTHS(REG_VEICULO.ANO_FABRI, 240)         
          WHERE ROWID = REG_VEICULO.ROWID;    
      END IF;
            
   END LOOP; 
   COMMIT;
END;
Responder
  • Informação
  • Quem está online

    Usuários navegando neste fórum: Nenhum usuário registrado e 17 visitantes