18

各イベントが0個以上の「スピーカー」と0個以上の「用語」に関連付けられている可能性がある「イベント」のテーブル、結合テーブルを介してイベントに関連付けられているレコードがある場合、列を持つすべてのイベントのテーブルを作成する必要があります各イベントに関連付けられた「speaker_names」と「term_names」のリストを表す各行。

ただし、クエリを実行すると、speaker_namesとterm_namesの値が重複しています。これは、結合テーブルが各スピーカーとイベントの用語の関連付けごとに行を生成するためです。

1|Soccer|Bobby|Ball
2|Baseball|Bobby - Bobby - Bobby|Ball - Bat - Helmets
3|Football|Bobby - Jane - Bobby - Jane|Ball - Ball - Helmets - Helmets

group_concat集計関数には、重複を削除する'distinct'を使用する機能がありますが、残念ながら、私が本当に必要としているカスタムセパレーターと一緒にそれをサポートしていません。私はこれらの結果を残されています:

1|Soccer|Bobby|Ball
2|Baseball|Bobby|Ball,Bat,Helmets
3|Football|Bobby,Jane|Ball,Helmets

私の質問はこれです:希望の結果を得るためにクエリを作成したり、データ構造を変更したりする方法はありますか?

これは必要なsqlite3クエリであり、Androidデプロイメント用であるため、カスタムC集計関数を追加できないことに注意してください。

考えられる解決策を簡単にテストできるようにする要点を作成しました:https ://gist.github.com/4072840

4

6 に答える 6

10

話者/用語名を互いに独立して検索します。

SELECT _id,
       name,
       (SELECT GROUP_CONCAT(name, ';')
        FROM events_speakers
        JOIN speakers
          ON events_speakers.speaker_id = speakers._id
        WHERE events_speakers.event_id = events._id
       ) AS speaker_names,
       (SELECT GROUP_CONCAT(name, ';')
        FROM events_terms
        JOIN terms
          ON events_terms.term_id = terms._id
        WHERE events_terms.event_id = events._id
       ) AS term_names
FROM events
于 2012-11-14T18:00:17.827 に答える
7

私もこの問題に遭遇しましたが、少し理解しやすい方法を思いつきました。SQLiteが報告するので、問題はメソッドにSQLite3::SQLException: DISTINCT aggregates must have exactly one argumentそれほど関係していないようですが、 ...内で使用することにあります。GROUP_CONCATDISTINCTGROUP_CONCAT

REPLACE実際には何もしないメソッド内にDISTINCT'subquery'をカプセル化すると、コンマのない文字列を適切に連結できるという欠点なしに、nawfalの提案を比較的単純にすることができます。

SELECT events._id, events.name, 
       (group_concat(replace(distinct speakers.name),'',''), ' - ') AS speaker_names, 
       (group_concat(replace(distinct speakers.name),'',''), ' - ') AS term_names 
FROM events 
LEFT JOIN 
   (SELECT et.event_id, ts.name 
    FROM terms ts 
    JOIN events_terms et ON ts._id = et.term_id
   ) terms ON events._id = terms.event_id 
LEFT JOIN 
   (SELECT sp._id, es.event_id, sp.name 
    FROM speakers sp 
    JOIN events_speakers es ON sp._id = es.speaker_id
   ) speakers ON events._id = speakers.event_id 
GROUP BY events._id;

しかし、実際にはこれをSQLiteのバグ/不整合と見なしますか、それとも何かが足りませんか?

于 2014-05-06T07:57:55.317 に答える
5

SQLiteがそれをサポートしていないのは奇妙です!。

それが役立つ場合にのみ、反対票を投じられるリスクがあります。

あなたは利用することができReplace(X, Y, Z)ます。,ただし、列に有効な値がないことを確認する必要があります。

SELECT events._id, events.name, 
       REPLACE(group_concat(distinct speakers.name), ',', ' - ') AS speaker_names, 
       REPLACE(group_concat(distinct terms.name), ',', ' - ') AS term_names 
FROM events 
LEFT JOIN 
   (SELECT et.event_id, ts.name 
    FROM terms ts 
    JOIN events_terms et ON ts._id = et.term_id
   ) terms ON events._id = terms.event_id 
LEFT JOIN 
   (SELECT sp._id, es.event_id, sp.name 
    FROM speakers sp 
    JOIN events_speakers es ON sp._id = es.speaker_id
   ) speakers ON events._id = speakers.event_id 
GROUP BY events._id;
于 2012-11-14T16:58:29.833 に答える
2

この問題は、group_concat(X、Y)式でのみ発生し、group_concat(X)式では発生しません。

group_concat(distinct X)はうまく機能します。

したがって、「、」が適切であれば問題はありませんが、「;」が必要な場合は問題ありません。'、'の代わりに(そして、元のテキストに'、'が含まれていないことは確かです)、次のことができます。

replace(group_concat(distinct X)、'、'、';')

于 2018-04-07T14:21:19.900 に答える
1

適切な回避策を提示するだけです(murbの答えは奇妙に括弧で囲まれています)。

問題:

group_concat(distinct column_name, 'custom_separator')custom_separatorの一部として取りますdistinct

解決:

SQLiteにそれが終了したことを知らせるためにいくつかのno-opが必要ですdistinct(個別にラップし、その引数をラップするため)。No-opは、2番目のパラメーターとして空の文字列に置き換えることができます(置き換えるドキュメント)。

group_concat(replace(distinct column_name, '', ''), 'custom_separator')

編集:

動作しないことがわかりました:-(-呼び出すことはできますが、distinctもう動作していません

于 2014-06-06T13:01:49.847 に答える
0

sqliteでは機能しない特殊なケースがあります:group_concat(DISTINCT X, Y) SQLでは使用できますがgroup_concat(DISTINCT X SEPARATOR Y)、sqliteでは使用できません

この例:Select group_concat(DISTINCT column1, '|') from example_table group by column2; 結果が得られます:DISTINCT集計には、1行目で引数が1つだけ必要です。

ソリューション :

select rtrim(replace(group_concat(DISTINCT column1||'@!'), '@!,', '|'),'@!') from example_table
于 2021-11-07T02:53:13.737 に答える