Aprenda PL/SQL

Ajuda com update usando filtros de outra tabela

Dúvidas, dicas e truques de SQL, Select, Update, Delete, cláusulas, operações com joins, Funções em SQLs, etc
  

Mensagemem Qua, 16 Mar 2016 9:34 pm

Boa noite pessoal,

Estou com uma dúvida que talvez seja simples, mas não sou muito bom em SQL e acabou surgindo uma necessidade que preciso resolver via banco.

Há alguns registros que devo alterar, porém para encontra-los utilizo filtros de 2 tabelas, vou usar de exemplo a tabela A e tabela B, o select faço dessa forma:

Código: Selecionar todos
SELECT * FROM A, B
       WHERE A.FILIAL = B.FILIAL
                AND A.FORNECEDOR = B.FORNECEDOR
                AND A.DATAENTRADA > '31/12/2011'
                AND A.DATAENTRADA < '01/01/2014'
                AND B.CSTPIS = '53'
                AND B.CSTCOFINS = '53'
                AND B.VALORPIS > 0
                AND B.VALORCOFINS > 0
                AND A.CODESP = '27'


Ele me traz 841 registros, eu preciso alterar o campo CODESP para '0', se eu faço com FOR UPDATE no fim e tento alterar manualmente um a um na tabela, ele me retorna um erro de ROWID INVÁLIDO.

Tentei fazer dessa forma e não deu certo:

Código: Selecionar todos
UPDATE A SET A.CODESP = (SELECT 0 FROM A, B
       WHERE A.FILIAL = B.FILIAL
                AND A.FORNECEDOR = B.FORNECEDOR
                AND A.DATAENTRADA > '31/12/2011'
                AND A.DATAENTRADA < '01/01/2014'
                AND B.CSTPIS = '53'
                AND B.CSTCOFINS = '53'
                AND B.VALORPIS > 0
                AND B.VALORCOFINS > 0
                AND A.CODESP = '27')


Mas ele retorna um erro pelo que parece que estou tentando colocar mais de 1 resultado por linha do update.

Alguém tem ideia de como posso fazer esse código.

Desde já, agradeço pela ajuda.
ThiagolRamos

Mensagemem Qui, 17 Mar 2016 7:06 am

Tenta se assim dá certo...

Código: Selecionar todos
update a
set a.codesp = (select 0
                from b
                where b.filial = a.filial
                  and b.fornecedor = a.fornecedor
                  and a.dataentrada > '31/12/2011'
                  and a.dataentrada < '01/01/2014'
                  and b.cstpis = '53'
                  and b.cstcofins = '53'
                  and b.valorpis > 0
                  and b.valorcofins > 0
                  and a.codesp = '27')
tiago_pimenta
Localização: Barretos / SP

Mensagemem Qui, 17 Mar 2016 7:23 am

Bom dia,

Ele apresentou uma mensagem de erro:

ORA-01407: não é possível atualizar ("NOMEDAINSTANCIA"."A"."CODESP") para NULL
ThiagolRamos

Mensagemem Qui, 17 Mar 2016 8:38 am

Roda o select interno e veja o que retorna !!! Provavelmente o select interno está retornando NULL e o campo no qual você está atualizando não aceita NULL
tiago_pimenta
Localização: Barretos / SP

Mensagemem Qui, 17 Mar 2016 9:04 am

Então, quando rodo o SELECT da forma que coloquei primeiro ele trás os resultados:

Código: Selecionar todos
SELECT 0 FROM A, B
       WHERE A.FILIAL = B.FILIAL
                AND A.FORNECEDOR = B.FORNECEDOR
                AND A.DATAENTRADA > '31/12/2011'
                AND A.DATAENTRADA < '01/01/2014'
                AND B.CSTPIS = '53'
                AND B.CSTCOFINS = '53'
                AND B.VALORPIS > 0
                AND B.VALORCOFINS > 0
                AND A.CODESP = '27'



Quando rodo da que você indicou:

Código: Selecionar todos
select 0
                from b
                where b.filial = a.filial
                  and b.fornecedor = a.fornecedor
                  and a.dataentrada > '31/12/2011'
                  and a.dataentrada < '01/01/2014'
                  and b.cstpis = '53'
                  and b.cstcofins = '53'
                  and b.valorpis > 0
                  and b.valorcofins > 0
                  and a.codesp = '27'


Ele não retorna nada, acredito que seja porque o FROM está referenciando só a tabela B, ai ele diz que o a.codesp não existe.
ThiagolRamos

Mensagemem Qui, 17 Mar 2016 2:39 pm

tiago_pimenta
Localização: Barretos / SP

Mensagemem Qui, 17 Mar 2016 3:22 pm

Boa tarde,

Acho que descobri o motivo do erro, mas ainda não a solução.

O select está trazendo mais de um resultado pois na tabela B que é a tabela de itens da nota, há mais de um item para cada registro da tabela A

Então ele traz por exemplo FORNECEDOR = 55 e NUMERO DA NOTA = 10 mas traz 3 registros desses.
ThiagolRamos

Mensagemem Qui, 17 Mar 2016 6:12 pm

Bom, acredito que você tenha duas soluções...

- Ver se não está faltando mas nenhum campo na "amarração";
- Colocar um distinct no select interno.
tiago_pimenta
Localização: Barretos / SP

Mensagemem Sex, 18 Mar 2016 6:59 am

Bom dia, pensei no distinct, mas fiquei com uma dúvida.

Ele é utilizado em apenas 1 campo, certo? Então se eu usasse no campo que tem o número da nota, ok, ele me traria apenas 1 registro para cada número de nota.

Mas se eu tiver 2 notas com o mesmo número, mas de fornecedores diferentes, ele trará apenas 1 registro ou ele fara a distinção dos dois por ter fornecedores diferentes?
ThiagolRamos



Voltar para SQL

Quem está online

Usuários navegando neste fórum: Bing [Bot] e 4 visitantes