質問編集履歴
3
my_commentsのCREATEを修正
test
CHANGED
File without changes
|
test
CHANGED
@@ -16,15 +16,16 @@
|
|
16
16
|
```SQL
|
17
17
|
-- コメント
|
18
18
|
CREATE TABLE my_comments(
|
19
|
-
`ID` int, `lang_id` int, `comment` varchar(10),
|
19
|
+
`ID` int, `lang_id` int, `comment` varchar(10), count_likes int(10),
|
20
|
-
PRIMARY KEY (`ID`)
|
20
|
+
PRIMARY KEY (`ID`),
|
21
|
+
FULLTEXT full_my_comments (`comment`) WITH PARSER ngram );
|
21
22
|
INSERT INTO my_comments
|
22
|
-
(`ID`, `lang_id`, `comment`)
|
23
|
+
(`ID`, `lang_id`, `comment`, `count_likes`)
|
23
24
|
VALUES
|
24
|
-
(1, 1, '眠らないでください'),
|
25
|
+
(1, 1, '眠らないでください', 5),
|
25
|
-
(2, 1, '静かにしてください'),
|
26
|
+
(2, 1, '静かにしてください', 1),
|
26
|
-
(3, 1, '席についてください'),
|
27
|
+
(3, 1, '席についてください', 6),
|
27
|
-
(4, 1, 'たまに休んで下さい');
|
28
|
+
(4, 1, 'たまに休んで下さい', 9);
|
28
29
|
|
29
30
|
-- タグ
|
30
31
|
CREATE TABLE my_tags(
|
2
文章の構成を修正
test
CHANGED
File without changes
|
test
CHANGED
@@ -1,15 +1,18 @@
|
|
1
1
|
### 実現したいこと
|
2
|
-
|
2
|
+
以下のCREATE、INSERTから、次の結果を得たいです。
|
3
|
-
|
4
|
-
### 発生している問題
|
5
|
-
後のPHPの`set_tag_datas_to_row()`で最終的に求めている値を得るために、次の`SELECT`を実行しています。
|
6
|
-
|
7
|
-
特に`GROUP_CONCAT`は「 tag_kind_id の値の数 ✕ カラムの数 」なので、次の`SELECT`では6つです。
|
8
|
-
|
9
|
-
|
3
|
+
これは '指導' のタグを持つコメントを取得した結果です。
|
4
|
+
|
10
|
-
|
5
|
+
```SQL
|
6
|
+
+----+----------------------+---------------------+--------------------------+-----------------+--------------------+---------------+
|
7
|
+
| ID | author_tag_names | author_is_officials | author_details | genre_tag_names | genre_is_officials | genre_details |
|
8
|
+
+----+----------------------+---------------------+--------------------------+-----------------+--------------------+---------------+
|
9
|
+
| 1 | 鈴木__SEPARATOR__佐藤 | 1__SEPARATOR__0 | 良い人__SEPARATOR__悪い人 | 指導 | 1 | . |
|
10
|
+
+----+----------------------+---------------------+--------------------------+-----------------+--------------------+---------------+
|
11
|
+
| 3 | NULL | NULL | NULL | 指導 | 1 | . |
|
12
|
+
+----+----------------------+---------------------+--------------------------+-----------------+--------------------+---------------+
|
13
|
+
```
|
14
|
+
|
11
|
-
###
|
15
|
+
### CREATE、INSERT
|
12
|
-
まずSQLで対象データの例です。
|
13
16
|
```SQL
|
14
17
|
-- コメント
|
15
18
|
CREATE TABLE my_comments(
|
@@ -46,11 +49,15 @@
|
|
46
49
|
(2, 4),
|
47
50
|
(3, 3);
|
48
51
|
```
|
49
|
-
|
52
|
+
### 実現するための自分なりのSELECT
|
50
|
-
こ
|
53
|
+
自分でこれを実現する場合は次のSELECTしか書けず、GROUP_CONCAT が多すぎてしまいます。
|
54
|
+
|
55
|
+
ご覧のように「GROUP_CONCAT の回数」は、「 tag_kind_id の値の数 ✕ カラムの数 」という2つで構想されているので、次のSELECTでは6回になっています…
|
56
|
+
|
57
|
+
…が、実際にはこの2つはもっと多いので GROUP_CONCAT だらけ(50回くらい)になってしまい、速度が遅くなるのです。
|
58
|
+
|
51
59
|
```SQL
|
52
|
-
-- タグ名を指定して検索
|
53
|
-
--
|
60
|
+
-- '指導' で検索した結果を取得
|
54
61
|
SELECT
|
55
62
|
comments.ID
|
56
63
|
|
@@ -117,15 +124,17 @@
|
|
117
124
|
|
118
125
|
-- タグ名を指定
|
119
126
|
WHERE
|
120
|
-
tags2.tag_name = '指導'
|
127
|
+
tags2.tag_name = '指導'
|
121
128
|
GROUP BY comments.ID
|
122
129
|
LIMIT 0, 5
|
123
130
|
|
124
131
|
```
|
132
|
+
|
133
|
+
### 補足
|
125
|
-
|
134
|
+
ちなみに、SELECTの結果には、PHPで次の`set_tag_datas_to_row()`をかけて、この`$result`が最終的にフロントへ出力する値として求めるものになります。
|
126
135
|
```PHP
|
127
136
|
<?php
|
128
|
-
// S
|
137
|
+
// SELECTの結果
|
129
138
|
$rows = [
|
130
139
|
['ID'=>1,
|
131
140
|
'author_tag_names'=>'鈴木__SEPARATOR__佐藤','author_is_officials'=>'1__SEPARATOR__0','author_details'=>'良い人__SEPARATOR__悪い人',
|
@@ -182,7 +191,7 @@
|
|
182
191
|
)
|
183
192
|
*/
|
184
193
|
|
185
|
-
//
|
194
|
+
// SELECTの結果に、tag_datas をセット
|
186
195
|
function set_tag_datas_to_row( $row ){
|
187
196
|
$result = [];
|
188
197
|
|
@@ -226,48 +235,6 @@
|
|
226
235
|
|
227
236
|
```
|
228
237
|
|
229
|
-
### 試したこと
|
230
|
-
通常の`CASE~WHEN~THEN`は次のようになりますが、
|
231
|
-
```SQL
|
232
|
-
CASE
|
233
|
-
WHEN 条件1 THEN カラムAの値
|
234
|
-
ELSE その他の値
|
235
|
-
END
|
236
|
-
```
|
237
|
-
次のように複数の値を指定できればいいなと思いました。
|
238
|
-
```SQL
|
239
|
-
CASE
|
240
|
-
WHEN 条件1 THEN カラムAの値, カラムBの値
|
241
|
-
ELSE その他の値
|
242
|
-
END
|
243
|
-
```
|
244
|
-
もしこのように指定できれば、先ほど提示した次のSQLは、
|
245
|
-
```SQL
|
246
|
-
# tag_kind_id=1 の tag_name
|
247
|
-
,GROUP_CONCAT(
|
248
|
-
CASE WHEN tags.tag_kind_id=1
|
249
|
-
THEN tags.tag_name
|
250
|
-
ELSE null END
|
251
|
-
) AS author_tag_names
|
252
|
-
|
253
|
-
# tag_kind_id=1 の is_official
|
254
|
-
,GROUP_CONCAT(
|
255
|
-
CASE WHEN tags.tag_kind_id=1
|
256
|
-
THEN tags.is_official
|
257
|
-
ELSE null END
|
258
|
-
) AS author_is_officials
|
259
|
-
```
|
260
|
-
|
261
|
-
次のように省略できますので、`GROUP_CONCAT`の数を「 tag_kind_id の値の数 ✕ カラムの数」ではなく「 tag_kind_id の値の数」にできると踏んだのですが…
|
262
|
-
```SQL
|
263
|
-
# tag_kind_id=1 の 各カラムの値
|
264
|
-
,GROUP_CONCAT(
|
265
|
-
CASE WHEN tags.tag_kind_id=1
|
266
|
-
THEN tags.tag_name, tags.is_official, tags.detail
|
267
|
-
ELSE null END
|
268
|
-
) AS author_datas
|
269
|
-
|
270
|
-
```
|
271
238
|
CREATE、INSERT、$result 以外は変えてしまって構いません。
|
272
239
|
この多すぎる`GROUP_CONCAT`をなんとか省略する方法を知りたいです。
|
273
240
|
宜しくお願いいたします。
|
1
SQL文を一部訂正
test
CHANGED
File without changes
|
test
CHANGED
@@ -263,7 +263,7 @@
|
|
263
263
|
# tag_kind_id=1 の 各カラムの値
|
264
264
|
,GROUP_CONCAT(
|
265
265
|
CASE WHEN tags.tag_kind_id=1
|
266
|
-
THEN tags.tag_name, tags.is_official
|
266
|
+
THEN tags.tag_name, tags.is_official, tags.detail
|
267
267
|
ELSE null END
|
268
268
|
) AS author_datas
|
269
269
|
|