Trocar linha por coluna

Dúvidas, dicas e truques de SQL, Select, Update, Delete, cláusulas, operações com joins, Funções em SQLs, etc
xprata
Rank: Analista Júnior
Rank: Analista Júnior
Mensagens: 93
Registrado em: Ter, 06 Abr 2010 11:31 am
Localização: São Paulo - SP

Boas senhores....

Preciso pegar o conteúdo da linha montar como coluna...estou com oracle 9, preciso do pivot, mas nesta versão acho que não tem correto?

tenho a seguinte informação na tabela

produto
laranja, fornecedor A tem o preço 1,0 e B preço 2,0
Maça, Fornecedor A preço 1,5 e C preço = 3,0
Uva Fornecedor X preço 5

Preciso de uma query para apresentar a informação da seguinte forma:

Coluna
Fornecedor A Fornecedor B Fornecedor C Fornecedor X
Linha Laranja 1,0 2,0
Maça 1,5 3,0
Uva 5,0

Detalhe o fornecedor é dinâmico, ou seja, pode ter E o F o Y, etc.

É isso ai....t+
Avatar do usuário
stcoutinho
Moderador
Moderador
Mensagens: 850
Registrado em: Qua, 11 Mai 2011 5:15 pm
Localização: são Paulo - SP

xprata,

Desculpe, mas teria a estrutura da tabela PRODUTOS?

Caso ela seja muito grande, então não precisaria ser a estrutura toda. Basta informar então somente os campos que você precisaria para montar sua querie.

Talvez com a estrutura da tabela (e um exemplo do conteúdo de cada campo) fique mais fácil montar para você uma solução que lhe atenda.

Abraços,

Sergio Coutinnho
xprata
Rank: Analista Júnior
Rank: Analista Júnior
Mensagens: 93
Registrado em: Ter, 06 Abr 2010 11:31 am
Localização: São Paulo - SP

No momento que postei já estava quase tombando de tanto trabalho e não vi como ficou o post....
Esta meio confuso mesmo....mas não da para desenha o layout, fica desposicionado.

Chamei de produto para facilitar, mas a query é resultado de alguns joins....

a primeira representação e apresentação do resultado da query que tenho

Nela trás a informação em dos produtos com seu preço para cada fornecedor...

Na segunda trás como preciso, ou seja tentar pivotear o fornecedor onde gostaria que ele virasse coluna. Tentei novamente mas não fica 100%
Veja ai se ajuda....valeu...


-------------For. A----- For. B-----For. C-----For. X
Laranja ----1,00 ----- 2,00
Maça ----- 1,50----------------------3,00
Uva--------------------------------------------------5,00
Avatar do usuário
stcoutinho
Moderador
Moderador
Mensagens: 850
Registrado em: Qua, 11 Mai 2011 5:15 pm
Localização: são Paulo - SP

Olá Xprata,

Compreendo sua impossibildade de apresentar uma estrutura de tabela (pois é um JOIN de várias tabelas).

Mas posso lhe dar uma sugestão? Vamos fazer de conta que existe uma tabela fictícia.

Siga estes passos:

A) Experimente criar uma VIEW com esta querie complexa que você falou;
B) Faça simplesmente o DESCRIBE desta VIEW. Desta forma você terá a "estrutura" da "tabela";
C) Elimine desta "estrutura fictícia de tabela" todos os campos que são desnecessários ao seu problema;
D) Acrescente esta estrutura aquí, com exemplo de pelo menos registros para 2 produtos ...

Feito tudo isso, fazemos de conta que "existe" uma tabela, com exemplos de registros "reais".

Quem sabe (com base nesta "estrutura fictícia") fica um pouco mais fácil para você explicar o que precisa?

Abraços,

Sergio Coutinho
xprata
Rank: Analista Júnior
Rank: Analista Júnior
Mensagens: 93
Registrado em: Ter, 06 Abr 2010 11:31 am
Localização: São Paulo - SP

Com este exemplo acho que fica mais claro

Selecionar tudo

select cargo
, max( decode(deptno, 10, total, null) ) dept_10
, max( decode(deptno, 20, total, null) ) dept_20
, max( decode(deptno, 30, total, null) ) dept_30
from ( select cargo, deptno, count(*) total
       from colaborador
       group by cargo, deptno )
este exemplo esta no link http://www.mhavila.com.br/topicos/bd/consulta_pivo.html

O detalhe é que os deptno são dinâmicos....portanto ora pode ter 10,20,30 ora pode ter 30,60,90
Avatar do usuário
stcoutinho
Moderador
Moderador
Mensagens: 850
Registrado em: Qua, 11 Mai 2011 5:15 pm
Localização: são Paulo - SP

Olá xprata,

Peço desculpas, mas realmente não saberia como aconselhar você, pois não tenho a estrutura das tabelas para me basear.

Mas creio que os demais foristas possam ter uma sugestão para ajudar você a resolver seu problema.

Te desejo boa sorte !

Sergio Coutinho
Avatar do usuário
stcoutinho
Moderador
Moderador
Mensagens: 850
Registrado em: Qua, 11 Mai 2011 5:15 pm
Localização: são Paulo - SP

Xprata,

Veja bem, no exemplo que você passou, existem DEPTO_10,DEPTO_20 e DEPTO_30. Só 3 departamentos.

Mas acredito que no enunciado do seu problema, você estava dizendo sobre FORNECEDOR_10, FORNECEDOR_20 ... FORNECEDOR_X. Creio que deve haver mais de 3 fornecedores (ou seja, "X" fornecedores).

Imagine o tamanho do seu SELECT (com código em HARDCODE) onde você precisaria colocar todos os seus valores ...

Eu acredito que a melhor solução seria você desenvolver uma rotina PL/SQL.

Não sei o quanto irá variar os seus fornecedores, mas experimente o seguinte:

1) Crie uma procedure e uma tabela GLOBAL TEMPORAY com a estrutura definitiva (fornecedor 1 .. até X);
2) Desenvolva uma procedure, que terá um cursor que lerá os dados de sua "querie monstro"
3) Para cada registro lido, ela fará

Selecionar tudo

      UPDATE .. 
            SET ..
       WHERE ..
      IF SQL%ROWCOUNT=0 THEN
          INSERT 
             INTO ...
            (COLUNAS)
             VALUES (VALORES)
     END IF;
4) Talvez as queries de UPDATE e INSERT possam ser dinâmicos, ou seja, você construirá um INSERT ou UPDATE diferente conforme o conteudo lido pelo cursor. Exemplo: Fornecedor = 10, então a querie dinâmica seria UPDATE .. SET FORNEC_10 = <valor> ...WHERE ..;
5) Carregada esta tabela, então você consegue recuperar os dados para este relatorio;

Me desculpe, estou sendo muito genérico nas recomendações, mas é o que conseguí fazer com base nas informações genéricas que me passou.

Boa sorte,

Sergio Coutinho
xprata
Rank: Analista Júnior
Rank: Analista Júnior
Mensagens: 93
Registrado em: Ter, 06 Abr 2010 11:31 am
Localização: São Paulo - SP

beleza...vou tentar fazer o que você esta falando....valeu pela ajuda...
Mas vou tentar fixar estes fornecedores...mas briga ta feia com o cliente...
mas sempre há um jeito pra resolver....
valeu :-)
Avatar do usuário
theand
Rank: Estagiário Sênior
Rank: Estagiário Sênior
Mensagens: 8
Registrado em: Qua, 23 Set 2009 11:58 am
Localização: SP

Acabei de implementar esse código.
Dá uma lida aqui :
http://glufke.net/oracle/viewtopic.php?f=2&t=8301

Selecionar tudo

declare
    v_query  varchar2(4000);
begin
    v_query := 'create table tmp3 (adm_tp  varchar2(2)
                                  ,itge_cd varchar2(30)
                                  ,itge_tp varchar2(1)
                                  ,itge_nm varchar2(500)';
    for cur in (select distinct tmp2.PACI_ID
                from   tmp2
                order  by tmp2.PACI_ID) loop
        v_query := v_query||', v_'||cur.paci_id||' varchar2(1000)';
    end loop;
    dbms_output.put_line(v_query||');');
    execute immediate v_query||')';
end;
Com base nos registros da tab2 ele monta as colunas da tab3.
As colunas ficam V_[pk] onde pk é o meu paci_id.
Responder
  • Informação
  • Quem está online

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