Desagrupar uma coluna no MYSQL
Gente estou com um problema e não achei resposta tenho uma consulta no MYSQL fiz select com duas tabelas e estão agrupadas por uma chave primaria eu quero desagrupar apenas um campo desta tabela que no caso são as datas de vencimento das parcelas.
Alguem pode me ajudar.
Alguem pode me ajudar.
Márcio
Curtidas 0
Melhor post
Marisiana Battistella
30/05/2015
Você pode postar o código?
Ficaria mais fácil entender e também poder te ajudar...
Ficaria mais fácil entender e também poder te ajudar...
GOSTEI 2
Mais Respostas
Márcio
30/05/2015
O codigo é o seguinte:
$sql = "SELECT *, MAX(paciente.num_parcelas)-SUM(financeira.parcelas_pg) AS 'parcelas_rest',
SUM(financeira.parcelas_pg) AS 'parcelas_pg1',
GROUP_CONCAT(venc_parcelas) AS 'venc_parc02'
FROM paciente inner join financeira on paciente.id = financeira.id_pac
where status=1
GROUP BY paciente.id
ORDER BY nome_pac ASC ";
No lugar de GROUP_CONCAT teria outro comando para poder exibir todos os "venc_parcelas" que está na tabela financeira pois está agrupado pelo GROUP BY e quero desagrupar só o "venc_parcelas".
A contatenação não satifaz o objetivo do sistema é possivél depois de agrupado desagrupar apenas esta a culuna "venc_parcelas" pois ela varia conforme o numero de parcelas porem ela é relacionada com o id da tabela paciente.
As tabelas "paciente e financeira" estão ligadas ao id e id_pac
$sql = "SELECT *, MAX(paciente.num_parcelas)-SUM(financeira.parcelas_pg) AS 'parcelas_rest',
SUM(financeira.parcelas_pg) AS 'parcelas_pg1',
GROUP_CONCAT(venc_parcelas) AS 'venc_parc02'
FROM paciente inner join financeira on paciente.id = financeira.id_pac
where status=1
GROUP BY paciente.id
ORDER BY nome_pac ASC ";
No lugar de GROUP_CONCAT teria outro comando para poder exibir todos os "venc_parcelas" que está na tabela financeira pois está agrupado pelo GROUP BY e quero desagrupar só o "venc_parcelas".
A contatenação não satifaz o objetivo do sistema é possivél depois de agrupado desagrupar apenas esta a culuna "venc_parcelas" pois ela varia conforme o numero de parcelas porem ela é relacionada com o id da tabela paciente.
As tabelas "paciente e financeira" estão ligadas ao id e id_pac
GOSTEI 1
Marisiana Battistella
30/05/2015
Entendi, mas o teu SQL precisa ser melhorado e eu acho que você não precisa desse GROUP_CONCAT.
Não utilize SELECT * informe os nomes dos campos que você precisa que o SQL retorne.
E o agrupamento não vai funcionar justamente porque você está agrupando pelo ID que é um valor único para cada registro.
Você pode postar a estrutura dessas duas tabelas (nomes dos campos, FK e PK ) ?
Não utilize SELECT * informe os nomes dos campos que você precisa que o SQL retorne.
E o agrupamento não vai funcionar justamente porque você está agrupando pelo ID que é um valor único para cada registro.
Você pode postar a estrutura dessas duas tabelas (nomes dos campos, FK e PK ) ?
GOSTEI 0
Márcio
30/05/2015
[img:descricao=TB financeira]http://arquivo.devmedia.com.br/forum/imagem/433925-20150531-001517.png[/img]
[img:descricao=TB paciente]http://arquivo.devmedia.com.br/forum/imagem/433925-20150531-001543.png[/img]
[img:descricao=TB paciente]http://arquivo.devmedia.com.br/forum/imagem/433925-20150531-001543.png[/img]
GOSTEI 0
Marisiana Battistella
30/05/2015
Você precisa listar as parcelas pagas e as parcelas restantes por data de vencimento das parcelas?
Veja se esse código se aproxima do que você precisa:
Veja se esse código se aproxima do que você precisa:
SELECT fin.venc_parcelas AS 'venc_parc02',
MAX(pac.num_parcelas) - SUM(fin.parcelas_pg) AS 'parcelas_rest',
SUM(fin.parcelas_pg) AS 'parcelas_pg1'
FROM paciente pac
INNER JOIN financeira fin
ON fin.id_pac = pac.id
WHERE pac.status=1
GROUP BY fin.venc_parcelas
ORDER BY pac.nome_pac ASC
GOSTEI 0
Márcio
30/05/2015
Se agrupar pelo venc_parcelas hora de exibir também aperceu o nome varias vezes testei este codigo preciso que apareça o nome uma vez e repita apenas as datas de cada paciente que está interligados ao id e id_pac com o concat deu um resultado quase bom pois quando exibe os dados ele concatena as datas de vencimentos não tem uma função de desagregação que possa ser usado com MAX ou MIN que possa desagregar apenas o campo esperado.
[img]http://arquivo.devmedia.com.br/forum/imagem/433925-20150531-145852.png[/img]
Esta é a imagem resultante do select. Preciso que em cada paciente mostre o campo venc_parcelas para determinado paciente mas mostre seu nome apenas uma vez.
[img]http://arquivo.devmedia.com.br/forum/imagem/433925-20150531-145852.png[/img]
Esta é a imagem resultante do select. Preciso que em cada paciente mostre o campo venc_parcelas para determinado paciente mas mostre seu nome apenas uma vez.
GOSTEI 0
Marisiana Battistella
30/05/2015
Nesse caso você precisa incluir o nome do paciente no retorno e no GROUP BY.
Na aplicação você terá que tratar a visualização dos dados...
Na aplicação você terá que tratar a visualização dos dados...
SELECT pac.nome_pac,
fin.venc_parcelas AS 'venc_parc02',
MAX(pac.num_parcelas) - SUM(fin.parcelas_pg) AS 'parcelas_rest',
SUM(fin.parcelas_pg) AS 'parcelas_pg1'
FROM paciente pac
INNER JOIN financeira fin
ON fin.id_pac = pac.id
WHERE pac.status=1
GROUP BY pac.nome_pac,
fin.venc_parcelas
ORDER BY pac.nome_pac ASC GOSTEI 1
Marisiana Battistella
30/05/2015
Outro ponto a ser analisado: Os valores que o SELECT retorna estão corretos? Você chegou a fazer essa conferência?
GOSTEI 0
Márcio
30/05/2015
Sim o restante está funcional e atende o unico problema é a questão de as datas de venc estão sendo agrupadas de forma que não atende vou testar o codigo que vc implementou mas desde já agradeço a disponibilidade.
GOSTEI 0
Márcio
30/05/2015
Mas o erro persiste ao executar o select todas as insindencias se repetem não consigo isolar a venc_parcelas vou tentar mudar a estrutura do BD financeira com campos dos pag para receber apenas um id_pac ou pensar outra coisa Mas agradeço.
GOSTEI 0
Marcos P
30/05/2015
Fica mais fácil para nós ajudarmos, se você criar a estrutura no Fiddle e colocar alguns registros para simularmos sua pesquisa !
GOSTEI 0
Márcio
30/05/2015
Coloquei http://sqlfiddle.com/#!9/6a148/4
Gente do jeito que está no representado é o que eu preciso.
Só quero substituir o GROUP_CONCAT mas nada o restante tá ok ainda falta tratar as casas decimais para valores mas isso é o de menos só preciso de uma forma de substituir o concat mas nada.
Eu não consegui uma função de "desagregação" quando faço a substituição do group by os nomes também são exibidos na real preciso que o nome apareça uma vez e as datas de venc que estão ligadas ao tal nome apareça em sua totalidade..
Na exibição dá o resultado que preciso porem preciso substiuir o concat.
Gente do jeito que está no representado é o que eu preciso.
Só quero substituir o GROUP_CONCAT mas nada o restante tá ok ainda falta tratar as casas decimais para valores mas isso é o de menos só preciso de uma forma de substituir o concat mas nada.
Eu não consegui uma função de "desagregação" quando faço a substituição do group by os nomes também são exibidos na real preciso que o nome apareça uma vez e as datas de venc que estão ligadas ao tal nome apareça em sua totalidade..
Na exibição dá o resultado que preciso porem preciso substiuir o concat.
GOSTEI 0
Marisiana Battistella
30/05/2015
Essa exibição dos dados é em um relatório?
Que ferramenta você está utilizando e qual é a linguagem de desenvolvimento?
Que ferramenta você está utilizando e qual é a linguagem de desenvolvimento?
GOSTEI 0
Márcio
30/05/2015
Este select vai gerar relatório sim mas o sistema é mais complexo a linguagem é PHP pois está rodando na web.
Mas a ferramenta tem hora que netbeens mas agora estou no dreamweaver para facilitar o uso de tabelas e formulários.
Mas a ferramenta tem hora que netbeens mas agora estou no dreamweaver para facilitar o uso de tabelas e formulários.
GOSTEI 0
Marcos P
30/05/2015
Mas a ferramenta tem hora que netbeens mas agora estou no dreamweaver para facilitar o uso de tabelas e formulários.
Não entendi essa frase !
Como contingência, você não consegue pegar os dados como está gerando agora e desmembrando-os do lado da aplicação ?
Em relação a query que você colocou no Fiddle, qual sua necessidade ?
Manter as totalizações (parcelas_rest e parcelas_pg1 ) e individualizar os vencimentos (venc_parc02)...
nome_pac parcelas_rest parcelas_pg1 venc_parc02 --------------- --------------- --------------- --------------- Carlos Barão 3 0 2015-06-21 Carlos Barão 3 0 2015-08-21 Carlos Barão 3 0 2015-07-21 Márcio André 5 0 2015-07-30 Márcio André 5 0 2015-09-30 Márcio André 5 0 2015-06-30 Márcio André 5 0 2015-08-30 Márcio André 5 0 2015-10-30
É isso ?
GOSTEI 0
Marisiana Battistella
30/05/2015
Se o retorno dos dados está correto, o problema não é o SQL, o que falta é programar na aplicação para fazer a visualização desses dados.
GOSTEI 0
Márcio
30/05/2015
Olha preciso que apareça : Aquele resultado sem o group concat só isso.
Na aplicação não é possível pois estou restringindo na sql e é preciso restringir é preciso uma solução ou na query ou mudar mesmo a estrutura do BD.
Minha necessidade é de puxar apenas uma vez o nome e o restante dos dados e 'venc_parc02' que é um alilas precisaria aparecer assim mas o concat ta falhando na hora de formatar a data.naquele exemplo foi o resultado que consegui até agora. só preciso substituir o concat, mas nada o restante pode ignorar.Só queria uma função para desagregar o 'venc_parc02' para o resultado ser este.
Carlos Barão 12/06/2015 21/07/2015 21/08/2015
Márcio André 30/06/2015 30/07/2015 30/08/2015 30/09/2015 30/10/2015
Na aplicação não é possível pois estou restringindo na sql e é preciso restringir é preciso uma solução ou na query ou mudar mesmo a estrutura do BD.
Minha necessidade é de puxar apenas uma vez o nome e o restante dos dados e 'venc_parc02' que é um alilas precisaria aparecer assim mas o concat ta falhando na hora de formatar a data.naquele exemplo foi o resultado que consegui até agora. só preciso substituir o concat, mas nada o restante pode ignorar.Só queria uma função para desagregar o 'venc_parc02' para o resultado ser este.
Carlos Barão 12/06/2015 21/07/2015 21/08/2015
Márcio André 30/06/2015 30/07/2015 30/08/2015 30/09/2015 30/10/2015
GOSTEI 0
Marcos P
30/05/2015
É isso ?
SELECT nome_pac, GROUP_CONCAT(venc_parcelas) AS 'venc_parc02' FROM paciente inner join financeira on paciente.id = financeira.id_pac where status=1 GROUP BY paciente.id ORDER BY nome_pac ASC
GOSTEI 0
Marisiana Battistella
30/05/2015
Antes de mudar a estrutura do banco, você tem que verificar o impacto que isso irá causar.
Realmente, observei os campos que constam no cadastro de clientes e tem informações de venda, aonde deveria constar apenas os dados dos clientes.
Isso deveria ter sido normalizado no momento da modelagem dos dados.
Esse sistema já está implantado?
Realmente, observei os campos que constam no cadastro de clientes e tem informações de venda, aonde deveria constar apenas os dados dos clientes.
Isso deveria ter sido normalizado no momento da modelagem dos dados.
Esse sistema já está implantado?
GOSTEI 0
Márcio
30/05/2015
Peguei o sistema para fazer algumas mudança as informações de compra da tabela paciente não são manipuláveis, são apenas informações que vão para o banco de dados quando o cliente estiver inativo. Agora a tabela financeira sei que tem que melhorar tipos de campos e mais algumas coisas.
O impacto está sendo avaliado pois não estou achando solução para o problema até já mostrei outro esboço para o cliente no qual aparece do jeito que ele quer, mas com um ponteiro no id. Assim aparece resultado único mas com eficiência.
Eu ainda não tinha me deparado com um problema igual e nunca achei que seria tão difícil a resolução.
O impacto está sendo avaliado pois não estou achando solução para o problema até já mostrei outro esboço para o cliente no qual aparece do jeito que ele quer, mas com um ponteiro no id. Assim aparece resultado único mas com eficiência.
Eu ainda não tinha me deparado com um problema igual e nunca achei que seria tão difícil a resolução.
GOSTEI 0
Márcio
30/05/2015
Usando o GROUP CONCAT não é possivél ter um resultado satisfatório pois data se transforma em string e não se formata com precisão. E isso pode comprometer a estabilidade do sistema.
O milagre era só substituir o group concat por uma função que desagregasse o campo 'venc_parcelas'.
Mas agradeço o esforço e agora que conheço o fórum estou sempre a disposição se eu puder ajudar .
O milagre era só substituir o group concat por uma função que desagregasse o campo 'venc_parcelas'.
Mas agradeço o esforço e agora que conheço o fórum estou sempre a disposição se eu puder ajudar .
GOSTEI 0
Marcos P
30/05/2015
marcim,
Continuo não entendo o resultado final que você precisa...
É isso que você precisa ?
Continuo não entendo o resultado final que você precisa...
É isso que você precisa ?
Carlos Barão 12/06/2015 Carlos Barão 21/07/2015 Carlos Barão 21/08/2015 Márcio André 30/06/2015 Márcio André 30/07/2015 Márcio André 30/08/2015 Márcio André 30/09/2015 Márcio André 30/10/2015
GOSTEI 0
Márcio
30/05/2015
É isso que preciso sem group concat: Entendeu?
Carlos Barão 12/06/2015 21/07/2015 21/08/2015
Márcio André 30/06/2015 30/07/2015 30/08/2015 30/09/2015 30/10/2015
SIMPLES ASSIM
Carlos Barão 12/06/2015 21/07/2015 21/08/2015
Márcio André 30/06/2015 30/07/2015 30/08/2015 30/09/2015 30/10/2015
SIMPLES ASSIM
GOSTEI 0
Marcos P
30/05/2015
Se você obtiver o resultado como coloquei acima...
Gerar a saída nesse formato, com a coluna de datas do tipo "date", resolveria seu problema ?
Suas strings de data estão sempre no formato "dd/mm/aaaa" ?
Carlos Barão 12/06/2015 Carlos Barão 21/07/2015 Carlos Barão 21/08/2015 Márcio André 30/06/2015 Márcio André 30/07/2015 Márcio André 30/08/2015 Márcio André 30/09/2015 Márcio André 30/10/2015
Gerar a saída nesse formato, com a coluna de datas do tipo "date", resolveria seu problema ?
Suas strings de data estão sempre no formato "dd/mm/aaaa" ?
GOSTEI 0
Márcio
30/05/2015
Este resultado foi o primeiro que alcancei porem quando gero o relatorio o nome também aparece veja a imagem que postei de um resultado se eu fizer assim como tá sugerindo para cada vencimento aparece uma todos os outros dado a unica solução aceitável e parece que não é possível pelo fato de agregar e depois desagregar é a ultima que postei esta abaixo.estou analisando e depurando o impacto que vai ter a mudança de estrutura do BD sendo que já possui dados na tabela original em uso.
Carlos Barão 12/06/2015 21/07/2015 21/08/2015
Márcio André 30/06/2015 30/07/2015 30/08/2015 30/09/2015 30/10/2015
Carlos Barão 12/06/2015 21/07/2015 21/08/2015
Márcio André 30/06/2015 30/07/2015 30/08/2015 30/09/2015 30/10/2015
GOSTEI 0
Márcio
30/05/2015
Os formatos de datas estão padrão MYSQL para poder manipular depois eu faço a formatação na saida ou entrada da query.
Pode ver no exemplo da tabela que estão padrão.
Pode ver no exemplo da tabela que estão padrão.
GOSTEI 0
Marcos P
30/05/2015
Usando o GROUP CONCAT não é possível ter um resultado satisfatório pois data se transforma em string e não se formata com precisão. E isso pode comprometer a estabilidade do sistema.
O milagre era só substituir o group concat por uma função que desagregasse o campo 'venc_parcelas'.
Sempre que você gerar um GROUP_CONCAT, a saída será gerada como string, por conta do separador entre os valores.
Considerando que as colunas são do tipo "Date" na origem, qual exatamente sua preocupação em relação ao formato não ser gerado com precisão no momento da concatenação ?
Mesmo gerando uma string, você consegue definir exatamente o formato de saída das datas ( via DATE_FORMAT ), padronizando-os.
Ainda, é possível definir o caracter de separação para identificar as diversas ocorrências de data, dentro da linha...
Datas nulas ( ou eventualmente inválidas ), você consegue tratar no WHERE... desprezando-as .
SELECT nome_pac, GROUP_CONCAT(DATE_FORMAT(venc_parcelas,'%d-%m-%Y') SEPARATOR ';') AS 'venc_parc02' FROM paciente inner join financeira on paciente.id = financeira.id_pac where status=1 GROUP BY paciente.id ORDER BY nome_pac ASC
Se você quiser gerar ocorrências individuais das datas, para tratá-las como campos separados no form da aplicação, gere o group simples com as datas :
SELECT DISTINCT paciente.id, paciente.Nome_pac, DATE_FORMAT(venc_parcelas,'%d-%m-%Y') AS 'venc_parc02' FROM paciente inner join financeira on paciente.id = financeira.id_pac where status=1 GROUP BY paciente.id, paciente.Nome_pac, DATE_FORMAT(venc_parcelas,'%Y-%m-%d') ORDER BY paciente.id,venc_parcelas
E depois coloque os valores separados do lado da aplicação...
( talvez uma grid, ficasse melhor para relacionar as parcelas )
[img]http://arquivo.devmedia.com.br/forum/imagem/378439-20150601-194439.png[/img]
Não descarte tratar isso na aplicação... pode ser a melhor solução !
GOSTEI 0
Márcio
30/05/2015
Olha este resultado que vc postou está perfeito e isso que preciso estou fazendo as mudanças na aplicação e format na query está resolvido.
Obrigado todos que contribuíram.
Obrigado todos que contribuíram.
GOSTEI 0
Marcos P
30/05/2015
Ótimo que resolveu...
GOSTEI 0
Márcio
30/05/2015
Estou mudando um pouco a aplicação o resultado da query continua insatisfatório mas vc me abriu outra porta estou tratando a plicação com java script e vou ver no que vai dar.
Mas as formatações de datas me ajudou muito obrigado.
Mas as formatações de datas me ajudou muito obrigado.
GOSTEI 0
Márcio
30/05/2015
Galera venho aqui agradecer ao fórum e ressaltar os colegas Marisiana e ao Marcos P pela ajuda prestada.
E também mostrar o resultado que está satisfatório e que foi fruto da boa vontade e paciência dos colegas do fórum.
[img]http://arquivo.devmedia.com.br/forum/imagem/433925-20150604-171344.png[/img]
Obrigado...
E também mostrar o resultado que está satisfatório e que foi fruto da boa vontade e paciência dos colegas do fórum.
[img]http://arquivo.devmedia.com.br/forum/imagem/433925-20150604-171344.png[/img]
Obrigado...
GOSTEI 0
Marcos P
30/05/2015
Marcim,
Se todos tivessem sua preocupação de retornar aos posts e informar o resultado final, nosso fórum seria muito melhor !
Parabéns e retorne por aqui, sempre que for possível !
Se todos tivessem sua preocupação de retornar aos posts e informar o resultado final, nosso fórum seria muito melhor !
Parabéns e retorne por aqui, sempre que for possível !
GOSTEI 1
Marisiana Battistella
30/05/2015
Obrigada pelo feedback Marcim!!
Fico feliz em poder contribuir.! =)
Fico feliz em poder contribuir.! =)
GOSTEI 1