Pertimbangkan tabel database yang menyimpan nama, dengan tiga baris:
Peter
Paul
Mary
Apakah ada cara mudah untuk mengubahnya menjadi satu string Peter, Paul, Mary
?
Pertimbangkan tabel database yang menyimpan nama, dengan tiga baris:
Peter
Paul
Mary
Apakah ada cara mudah untuk mengubahnya menjadi satu string Peter, Paul, Mary
?
Jawaban:
Jika Anda menggunakan SQL Server 2017 atau Azure, lihat jawaban Mathieu Renda .
Saya memiliki masalah yang sama ketika saya mencoba untuk bergabung dengan dua tabel dengan hubungan satu ke banyak. Dalam SQL 2005 saya menemukan bahwa
XML PATH
metode dapat menangani penggabungan baris dengan sangat mudah.Jika ada tabel yang disebut
STUDENTS
Hasil yang saya harapkan adalah:
Saya menggunakan yang berikut ini
T-SQL
:Anda dapat melakukan hal yang sama dengan cara yang lebih kompak jika Anda dapat menyatukan koma di awal dan menggunakan
substring
untuk melewati yang pertama sehingga Anda tidak perlu melakukan sub-permintaan:sumber
<
atau&
. Lihat @ BenHinman komentar.FOR XML PATH ('')
. Itu berarti itu tidak dapat dianggap andal karena setiap patch atau pembaruan dapat mengubah cara kerjanya. Ini pada dasarnya mengandalkan fitur yang sudah usang.FOR XML
ini dimaksudkan untuk menghasilkan XML, bukan string acak. Itulah mengapa lolos&
,<
dan>
untuk kode XML entitas (&
,<
,>
). Saya menganggap itu juga akan melarikan diri"
dan'
ke"
dan'
dalam atribut juga. Ini tidakGROUP_CONCAT()
,string_agg()
,array_agg()
,listagg()
, dll bahkan jika Anda dapat jenis make melakukan itu. Kita harus menghabiskan waktu kita menuntut Microsoft menerapkan fungsi yang tepat.string_agg
di v.Next. dan semua ini bisa hilang.Gunakan
COALESCE
:Hanya beberapa penjelasan (karena jawaban ini tampaknya mendapatkan pandangan yang relatif teratur):
1) Tidak perlu menginisialisasi
@Names
dengan nilai string kosong.2) Tidak perlu melepas pemisah tambahan di akhir.
@Names
NULL setelah baris itu, dan baris berikutnya akan memulai kembali sebagai string kosong lagi. Mudah diperbaiki dengan satu dari dua solusi:atau:
Bergantung pada perilaku apa yang Anda inginkan (opsi pertama hanya menyaring NULL keluar, opsi kedua menyimpannya dalam daftar dengan pesan penanda [ganti 'N / A' dengan apa pun yang sesuai untuk Anda]).
sumber
SQL Server 2017+ dan SQL Azure: STRING_AGG
Dimulai dengan versi SQL Server berikutnya, kita akhirnya bisa menyatukan seluruh baris tanpa harus menggunakan variabel apa pun atau sihir XML.
STRING_AGG (Transact-SQL)
Tanpa pengelompokan
Dengan pengelompokan:
Dengan pengelompokan dan sub-sortasi
sumber
Salah satu metode yang belum ditampilkan melalui
XML
data()
perintah di MS SQL Server adalah:Asumsikan tabel bernama NameList dengan satu kolom bernama FName,
pengembalian:
Hanya koma ekstra yang harus ditangani.
Sunting: Seperti yang diadopsi dari komentar @ NReilingh, Anda dapat menggunakan metode berikut untuk menghapus koma tertinggal. Dengan asumsi nama tabel dan kolom yang sama:
sumber
+ ', '
masih menambahkan satu ruang di antara setiap elemen gabungan.SELECT STUFF(REPLACE((SELECT '#!'+city AS 'data()' FROM #cityzip FOR XML PATH ('')),' #!',', '),1,2,'')
Dalam SQL Server 2005
Di SQL Server 2016
Anda dapat menggunakan sintaks FOR JSON
yaitu
Dan hasilnya akan menjadi
Ini akan berfungsi bahkan data Anda mengandung karakter XML yang tidak valid
yang
'"},{"_":"'
aman karena jika data yang mengandung'"},{"_":"',
itu akan melarikan diri ke"},{\"_\":\"
Anda dapat mengganti
', '
dengan pemisah string apa punDan di SQL Server 2017, Azure SQL Database
Anda dapat menggunakan fungsi STRING_AGG baru
sumber
<
,>
,&
, dll, yangFOR XML PATH('')
secara otomatis akan melarikan diri.Di MySQL ada fungsi, GROUP_CONCAT () , yang memungkinkan Anda menggabungkan nilai dari beberapa baris. Contoh:
sumber
SEPARATOR '", "'
saya akan kehilangan beberapa karakter di akhir entri terakhir. mengapa ini bisa terjadi?CHAR
, Anda harus melemparkannya, misalnya melaluiGROUP_CONCAT( CAST(id AS CHAR(8)) ORDER BY id ASC SEPARATOR ',')
2) jika Anda memiliki banyak nilai yang datang, Anda harus meningkatkangroup_concat_max_len
seperti yang tertulis di stackoverflow.com/a/1278210/1498405Gunakan COALESCE - Pelajari lebih lanjut dari sini
Sebagai contoh:
Kemudian tulis kode di bawah ini di sql server,
Outputnya adalah:
sumber
Declare @Numbers AS Nvarchar(MAX)
dan itu bekerja dengan baik. Bisakah Anda jelaskan mengapa Anda merekomendasikan untuk tidak menggunakannya?Array postgres mengagumkan. Contoh:
Buat beberapa data uji:
Gabungkan mereka dalam sebuah array:
Konversi array menjadi string yang dibatasi koma:
DIBUAT
Sejak PostgreSQL 9.0 bahkan lebih mudah .
sumber
select array_to_string(array_agg(name||'('||id||')'
Oracle 11g Release 2 mendukung fungsi LISTAGG. Dokumentasi di sini .
Peringatan
Hati-hati menerapkan fungsi ini jika ada kemungkinan string yang dihasilkan melebihi 4000 karakter. Itu akan melempar pengecualian. Jika itu yang terjadi maka Anda perlu menangani pengecualian atau memutar fungsi Anda sendiri yang mencegah string yang tergabung untuk lebih dari 4000 karakter.
sumber
LISTAGG
bekerja dengan sempurna! Baca saja dokumen yang tertaut di sini.wm_concat
dihapus dari versi 12c dan seterusnya.Di SQL Server 2005 dan yang lebih baru, gunakan kueri di bawah ini untuk menyatukan baris.
sumber
<
atau&
.Saya tidak memiliki akses ke SQL Server di rumah, jadi saya kira sintaks di sini, tetapi lebih atau kurang:
sumber
SELECT @names = @names + CASE WHEN LEN(@names)=0 THEN '' ELSE ' ' END + Name FROM Names
SELECT @names = @names + ISNULL(' ' + Name, '')
Solusi CTE rekursif disarankan, tetapi tidak ada kode yang diberikan. Kode di bawah ini adalah contoh CTE rekursif. Perhatikan bahwa meskipun hasilnya cocok dengan pertanyaan, data tidak cukup cocok dengan deskripsi yang diberikan, karena saya berasumsi bahwa Anda benar-benar ingin melakukan ini pada grup baris, tidak semua baris dalam tabel. Mengubahnya untuk mencocokkan semua baris dalam tabel dibiarkan sebagai latihan untuk pembaca.
sumber
name
kolom ke dalam string dipisahkan koma selama 4 kelompok dariid
s. Pada pandangan pertama, saya pikir ini lebih berfungsi daripada apa yang dilakukan kebanyakan solusi lain untuk SQL Server.Dimulai dengan PostgreSQL 9.0 ini cukup sederhana:
Dalam versi sebelum 9.0
array_agg()
dapat digunakan seperti yang ditunjukkan oleh hgmnzsumber
SELECT string_agg(non_text_type::text, ',') FROM table
varchar
atauchar
Anda perlu membuat variabel yang akan menampung hasil akhir Anda dan memilih ke dalamnya, seperti itu.
Solusi termudah
sumber
Dalam SQL Server vNext ini akan dibangun dengan fungsi STRING_AGG, baca lebih lanjut di sini: https://msdn.microsoft.com/en-us/library/mt790580.aspx
sumber
Menggunakan XML membantu saya memisahkan baris dengan koma. Untuk koma ekstra kita dapat menggunakan fungsi ganti dari SQL Server. Alih-alih menambahkan koma, penggunaan AS 'data ()' akan menyatukan baris dengan spasi, yang nantinya dapat diganti dengan koma seperti sintaks yang ditulis di bawah ini.
sumber
Solusi siap pakai, tanpa koma tambahan:
Daftar kosong akan menghasilkan nilai NULL. Biasanya Anda akan memasukkan daftar ke dalam kolom tabel atau variabel program: sesuaikan panjang maks 255 dengan kebutuhan Anda.
(Diwakar dan Jens Frandsen memberikan jawaban yang baik, tetapi perlu perbaikan.)
sumber
', '
dengan','
jika Anda tidak menginginkan ruang ekstra.Berikut ini contohnya:
sumber
Ini menempatkan koma liar di awal.
Namun, jika Anda membutuhkan kolom lain, atau CSV tabel anak, Anda harus membungkusnya dalam bidang yang ditentukan pengguna skalar (UDF).
Anda dapat menggunakan jalur XML sebagai subquery berkorelasi dalam klausa SELECT juga (tapi saya harus menunggu sampai saya kembali bekerja karena Google tidak melakukan pekerjaan di rumah :-)
sumber
Dengan jawaban lain, orang yang membaca jawabannya harus mengetahui tabel domain tertentu seperti kendaraan atau siswa. Tabel harus dibuat dan diisi dengan data untuk menguji solusi.
Di bawah ini adalah contoh yang menggunakan tabel SQL Server "Information_Schema.Columns". Dengan menggunakan solusi ini, tidak perlu membuat tabel atau data ditambahkan. Contoh ini membuat daftar nama kolom yang dipisahkan koma untuk semua tabel dalam database.
sumber
Untuk Oracle DB, lihat pertanyaan ini: Bagaimana beberapa baris dapat digabungkan menjadi satu di Oracle tanpa membuat prosedur tersimpan?
Jawaban terbaik tampaknya oleh @Emmanuel, menggunakan fungsi LISTAGG () bawaan, tersedia di Oracle 11g Release 2 dan yang lebih baru.
seperti yang ditunjukkan oleh @ user762952, dan menurut dokumentasi Oracle http://www.oracle-base.com/articles/misc/string-aggregation-techniques.php , fungsi WM_CONCAT () juga merupakan opsi. Tampaknya stabil, tetapi Oracle secara eksplisit merekomendasikan untuk tidak menggunakannya untuk aplikasi SQL apa pun, jadi gunakan dengan risiko Anda sendiri.
Selain itu, Anda harus menulis fungsi Anda sendiri; dokumen Oracle di atas memiliki panduan tentang cara melakukan itu.
sumber
Untuk menghindari nilai nol, Anda dapat menggunakan CONCAT ()
sumber
Saya sangat menyukai keanggunan jawaban Dana . Hanya ingin membuatnya lengkap.
sumber
SELECT @names = @names + CASE WHEN LEN(@names)=0 THEN '' ELSE ', ' END + Name FROM Names
kemudian Anda tidak harus memotongnya setelah itu.Jawaban ini akan membutuhkan beberapa hak istimewa di server untuk bekerja.
Assemblies adalah pilihan yang bagus untuk Anda. Ada banyak situs yang menjelaskan cara membuatnya. Yang saya pikir sangat baik dijelaskan apakah ini salah satu
Jika Anda mau, saya sudah membuat perakitan, dan dimungkinkan untuk mengunduh DLL di sini .
Setelah Anda mengunduhnya, Anda harus menjalankan skrip berikut di SQL Server Anda:
Perhatikan bahwa jalur menuju perakitan mungkin dapat diakses ke server. Karena Anda telah berhasil melakukan semua langkah, Anda dapat menggunakan fungsi seperti:
Semoga bisa membantu !!!
sumber
Contoh lengkap MySQL:
Kami memiliki Pengguna yang dapat memiliki banyak Data dan kami ingin memiliki keluaran, di mana kami dapat melihat semua data pengguna dalam daftar:
Hasil:
Pengaturan meja:
Pertanyaan:
sumber
Saya biasanya menggunakan pilih seperti ini untuk menggabungkan string di SQL Server:
sumber
Jika Anda ingin berurusan dengan nol, Anda dapat melakukannya dengan menambahkan klausa di mana atau menambahkan COALESCE lain di sekitar yang pertama.
sumber
Ini bekerja untuk saya ( SqlServer 2016 ):
Inilah sumbernya: https://www.mytecbits.com/
Dan solusi untuk MySql (karena halaman ini muncul di Google untuk MySql)
Dari Dokumentasi MySql
sumber
Di Oracle, itu
wm_concat
. Saya percaya fungsi ini tersedia dalam rilis 10g dan lebih tinggi.sumber
Ini juga bisa bermanfaat
kembali
sumber