Urutan array_agg PostgreSQL

107

Tabel 'hewan':

animal_name animal_type
Tom         Cat
Jerry       Mouse
Kermit      Frog

Pertanyaan:

SELECT 
array_to_string(array_agg(animal_name),';') animal_names,
array_to_string(array_agg(animal_type),';') animal_types
FROM animals;

Hasil yang diharapkan:

Tom;Jerry;Kerimt, Cat;Mouse;Frog
OR
Tom;Kerimt;Jerry, Cat;Frog;Mouse

Dapatkah saya yakin bahwa urutan fungsi agregat pertama akan selalu sama seperti urutan kedua. Maksud saya, saya tidak ingin mendapatkan:

Tom;Jerry;Kermit, Frog;Mouse,Cat
Olo
sumber
7
Jika Anda menggunakan 9.0, Anda dapat mengganti panggilan bersarang dengan satustring_agg()
a_horse_with_no_name

Jawaban:

27

Jika Anda menggunakan versi PostgreSQL <9.0 maka:

Dari: http://www.postgresql.org/docs/8.4/static/functions-aggregate.html

Dalam implementasi saat ini, urutan input pada prinsipnya tidak ditentukan. Namun, memberikan nilai input dari subkueri yang diurutkan biasanya akan berfungsi. Sebagai contoh:

PILIH xmlagg (x) FROM (SELECT x FROM test ORDER BY y DESC) AS tab;

Jadi dalam kasus Anda, Anda akan menulis:

SELECT
array_to_string(array_agg(animal_name),';') animal_names,
array_to_string(array_agg(animal_type),';') animal_types
FROM (SELECT animal_name, animal_type FROM animals) AS x;

Masukan ke array_agg kemudian tidak akan diurutkan tetapi akan sama di kedua kolom. Dan jika Anda mau, Anda bisa menambahkan ORDER BYklausa ke subkueri.

UlfR
sumber
331

Gunakan ORDER BY, seperti contoh dari manual ini :

SELECT array_agg(a ORDER BY b DESC) FROM table;
Frank Heikens
sumber
42
Catatan: ORDER BYin array_aggdiperkenalkan di PostgreSQL 9
UlfR
6
Jauh lebih baik daripada jawaban yang diterima dengan asumsi PostgreSQL 9+.
Erik
1
Bisakah Anda memberi sampel dengan ORDER BY untuk dipilih: SELECT array_agg (animal_name), array_agg (animal_type) FROM animals; ?
Grigory Kislin
9
Perhatikan bahwa ini tidak bekerja untukarray_agg(DISTINCT a ORDER BY b)
cerd
1
Saat menggunakan untuk beberapa kolom, Anda harus menambahkan tanda kurung:array_agg((a, b, c) ORDER BY b)
bennos