Ok, eu tenho uma tabela com uma chave indexada e um campo não indexado. Preciso encontrar todos os registros com um determinado valor e retornar a linha. Gostaria de saber se posso pedir por vários valores.
Exemplo:
id x_field
-- -----
123 a
124 a
125 a
126 b
127 f
128 b
129 a
130 x
131 x
132 b
133 p
134 p
135 i
pseudo: gostaria que os resultados fossem ordenados assim, where ORDER BY x_field = 'f', 'p', 'i', 'a'
SELECT *
FROM table
WHERE id NOT IN (126)
ORDER BY x_field 'f', 'p', 'i', 'a'
Portanto, os resultados seriam:
id x_field
-- -----
127 f
133 p
134 p
135 i
123 a
124 a
125 a
129 a
A sintaxe é válida, mas quando executo a consulta, ela nunca retorna nenhum resultado, mesmo se eu limitar a 1 registro. Existe outra maneira de fazer isso?
Pense no x_field como resultados de teste e eu preciso validar todos os registros que se enquadram na condição. Eu queria ordenar os resultados do teste por valores com falha, valores aprovados. Portanto, eu poderia validar os valores com falha primeiro e, em seguida, os valores passados usando o ORDER BY.
O que não posso fazer:
- GROUP BY, pois preciso retornar os valores de registro específicos
- ONDE x_field IN ('f', 'p', 'i', 'a'), preciso de todos os valores, pois estou tentando usar uma consulta para vários testes de validação. E os valores x_field não estão na ordem DESC / ASC
Depois de escrever essa pergunta estou começando a pensar que preciso repensar isso, LOL!
fonte
Respostas:
fonte
Você pode usar um LEFT JOIN com "VALUES ('f', 1), ('p', 2), ('a', 3), ('i', 4)" e usar a segunda coluna em seu pedido -por expressão. O Postgres usará um Hash Join que será muito mais rápido do que um CASE enorme se você tiver muitos valores. E é mais fácil de gerar automaticamente.
Se essas informações de pedido forem fixas, ela deverá ter sua própria tabela.
fonte
Experimentar:
Você estava no caminho certo, mas ao colocar x_field apenas no valor F, os outros 3 foram tratados como constantes e não comparados com nada no conjunto de dados.
fonte
Use uma
case
chave para traduzir os códigos em números que podem ser classificados:fonte
Encontrei uma solução muito mais limpa para isso:
Observação: array_position precisa do Postgres v9.5 ou superior.
fonte
array_position(ARRAY[1, 0]::integer[], x_field)
As sugestões
CASE
eORDER BY
devem funcionar, mas vou sugerir um cavalo de uma cor diferente. Supondo que haja apenas um número razoável de valores parax_field
e você já sabe quais são, crie um tipo enumerado com F, P, A e I como os valores (além de quaisquer outros valores possíveis aplicáveis). Enums serão classificados na ordem indicada por suaCREATE
declaração. Além disso, você pode usar nomes de valor significativos - seu aplicativo real provavelmente usa e você acabou de mascará-los para confidencialidade - sem desperdiçar espaço, uma vez que apenas a posição ordinal é armazenada.fonte
Você pode ordenar por uma coluna selecionada ou outras expressões.
Aqui está um exemplo de como ordenar pelo resultado de uma instrução case:
O resultado será uma lista começando com "IsGen = 0" linhas, seguido por "IsGen = 1" linhas e todas as outras linhas no final.
Você pode adicionar mais parâmetros de pedido no final:
fonte
Para alguém que é novo no ORDER BY com CASE, isso pode ser útil
fonte
você pode usar a posição (texto no texto) para ordenar a sequência
fonte