30

SOでいくつかのトピックを見つけましたが、それでもクエリの適切な設定を見つけることができません。

これはクエリであり、ローカルホストでうまく機能します。

@cars = Car.find_by_sql('SELECT cars.*, COUNT(cars.id) AS counter 
                         FROM cars 
                         LEFT JOIN users ON cars.id=users.car_id 
                         GROUP BY cars.id ORDER BY counter DESC')

しかし、Herokuでは、上記のエラーが発生します-GROUP BY句、または集計関数で使用されます

次に、テーブル内のすべての列を指定する必要があることをどこかで読んだので、これを試しました。

@cars = Car.find_by_sql('SELECT cars.id, cars.name, cars.created_at, 
                                cars.updated_at, COUNT(cars.id) AS counter 
                         FROM cars 
                         LEFT JOIN users ON cars.id=users.car_id 
                         GROUP BY (cars.id, cars.name, cars.created_at, cars.updated_at) 
                         ORDER BY counter DESC')

しかし、これはローカルホストでは機能せず、Herokuでも機能しません...

クエリの正しい構成は何である必要がありますか?

4

3 に答える 3

33

このようなクエリ(すべてまたはほとんどの行を取得する)は、前に行うと高速GROUPになりますJOIN。このような:

SELECT id, name, created_at, updated_at, u.ct
FROM   cars c
LEFT   JOIN (
    SELECT car_id, count(*) AS ct
    FROM   users
    GROUP  BY 1
    ) u ON u.car_id  = c.id
ORDER  BY u.ct DESC;

これにより、必要な結合操作がはるかに少なくなります。また、テーブルの行は、cars最初に多くのユーザーに参加して乗算し、次にグループ化して再度一意にする必要はありません。
適切なテーブルのみをグループ化する必要があるため、ロジックも単純になります。

于 2012-04-16T00:01:54.843 に答える
28

同じ列で集計してグループ化しようとしていると思います。必要なデータによって異なります。エーテルはこれを行います:

SELECT 
 cars.name, 
 cars.created_at, 
 cars.updated_at, 
 COUNT(cars.id) AS counter 
FROM cars 
LEFT JOIN users 
  ON cars.id=users.car_id 
GROUP BY cars.name, cars.created_at, cars.updated_at 
ORDER BY counter DESC

またはあなたは多分すべてを数えたいですか?次に、このように:

SELECT
 cars.id,
 cars.name, 
 cars.created_at, 
 cars.updated_at, 
 COUNT(*) AS counter 
FROM cars 
LEFT JOIN users 
  ON cars.id=users.car_id 
GROUP BY cars.id, cars.name, cars.created_at, cars.updated_at 
ORDER BY counter DESC
于 2012-04-15T11:45:14.207 に答える
8

あなたはMAX()車のコラムでトリックを使うことができます。

@cars = Car.find_by_sql('
SELECT cars.id, MAX(cars.name) as name, MAX(cars.created_at) AS 
created_at, MAX(cars.updated_at) as updated_at, COUNT(cars.id) AS counter 
FROM cars LEFT JOIN users ON cars.id=users.car_id 
GROUP BY cars.id ORDER BY counter DESC')
于 2012-04-15T11:51:42.197 に答える