0

ランダムに3つスタンプをもらいたいのですが、それぞれ国が異なります。このクエリはランダムなスタンプを返しますが、同じ国からのものである可能性があります。GROUP BY country_idを追加すると、さまざまな国の3つのスタンプが取得されますが、各国の最初のスタンプのみが取得されます。

SELECT `stamps`.`stamp_id`, `countries`.`country_name_cs` FROM `stamps`
LEFT JOIN `countries` ON countries.country_id = stamps.country_id
WHERE (stamps.stamp_enabled = 1) ORDER BY rand() ASC LIMIT 3

何か案が?

プロファイルのクエリ(#Ezequiel Munsソリューション)

starting              0.000232
Opening tables        0.000047
System lock           0.000013
Table lock            0.000635
optimizing            0.000036
statistics            0.000022
preparing             0.000023
Creating tmp table    0.000293
executing             0.000004
Copying to tmp table  0.060066
Sorting result        0.013835
Sending data          0.089164
removing tmp table    0.000632
Sending data          0.000026
init                  0.000048
optimizing            0.000014
statistics            0.000061
preparing             0.000028
Creating tmp table    0.000326
executing             0.000004
Copying to tmp table  0.353176
Sorting result        0.000158
Sending data          0.000038
end                   0.000005
removing tmp table    0.000018
end                   0.000006
query end             0.000004
freeing items         0.000575
removing tmp table    0.002363
closing tables        0.000023
logging slow query    0.000004
cleaning up           0.000009

id      select_type       table      type       possible_keys       key         key_len     ref           rows      Extra
1       PRIMARY       <derived2>     ALL        NULL                NULL        NULL        NULL          12679     Using temporary; Using filesort
1       PRIMARY       c              eq_ref     PRIMARY             PRIMARY     4           s.country_id  1      
2       DERIVED       stamps         ALL        NULL                NULL        NULL        NULL          12679     Using where; Using temporary; Using filesort
4

2 に答える 2

2
SELECT
    c.country_id,
    c.country_name_cs,
    s.stamp_id
FROM country c
    JOIN (
        SELECT * 
        FROM stamps
        WHERE stamp_enabled = 1
        ORDER BY RAND()
    ) AS s ON c.country_id = s.country_id
GROUP BY c.country_id, c.country_name_cs
ORDER BY RAND()
LIMIT 3;

最初にすべての国をそれぞれのスタンプにランダムな順序で参加させ、次にそのリストを各国の最初の(ランダムに選択された)スタンプにトリミングしてグループ化します。外側のクエリのORDERBYは、選択した国をランダム化し、LIMITは3つだけを返します。

デビッドZが言ったように、非効率的です。

于 2012-04-23T08:48:12.887 に答える
1

次のクエリを試すことができます。これにより、最初に3つのランダムな国が選択され、混合スタンプテーブルを使用して結合が実行され、次に国ごとにグループ化されます。効率的ではありませんが、小さなデータセットでは機能します。

 SELECT
    mixed_stamp.stamp_id,
    random.country_name_cs
 FROM
    (SELECT * FROM stamps ORDER BY RAND()) AS mixed_stamp
 LEFT JOIN (SELECT country_id FROM countries ORDER BY RAND() LIMIT 3) random ON (random.country_id = mixed_stamp.country_id)
 GROUP BY random.country_id
于 2012-04-23T08:18:07.487 に答える