結合で重複のエラーが発生!カラムのidがどれなのかが分からない原因は?

このQ&Aのポイント
  • 結合で重複のエラーが発生しています。おそらくカラムのidが結合の中で重複しているという内容ですが、どれのidが重複しているのかが分かりません。
  • サブクエリの実行までは問題ありませんが、最終的には「tbl2sbelongs」テーブルの「count」の値によって「tbl1s」を降順に並べ替えたいと考えています。
  • テーブル「tbl1s」にはidが1, 2, 3のレコードがあり、テーブル「tbl2s」にもidが1, 2, 3のレコードがあります。テーブル「tbl1s_tbl2s」には結合されたレコードが、「tbl2sbelongs」テーブルには各tbl2_idごとのcountの値があります。結合の中でidが重複しているため、エラーが発生しています。
回答を見る
  • ベストアンサー

結合で重複のエラーが出る

mysql5.1.33を使用しています。 次のような構成で、 テーブル「tbl1s」 id int(11) テーブル「tbl2s」 id int(11) テーブル「tbl1s_tbl2s」 id int(11) tbl1_id int(11) tbl1sの外部キー tbl2_id int(11) tbl2sの外部キー テーブル「tbl2sbelongs」 id int(11) tbl2_id int(11) tbl2sの外部キー count int(11) テーブル「tbl1s」 +------+ |  id  | +------+ |  1  | +------+ |  2  | +------+ |  3  | +------+ テーブル「tbl2s」 +------+ |  id  | +------+ |  1  | +------+ |  2  | +------+ |  3  | +------+ テーブル「tbl1s_tbl2s」 +------+-------+-------+ |  id  | tbl1_id | tbl2_id | +------+-------+-------+ |  1  | 1    | 1   | +------+-------+------+ |  2  | 1    | 2   | +------+-------+------+ |  3  | 3    | 3   | +------+-------+------+ テーブル「tbl2sbelongs」 +------+-------+-------+ |  id  | tbl2_id | count | +------+-------+-------+ |  1  | 1    | 3   | +------+-------+------+ |  2  | 2    | 10  | +------+-------+------+ |  3  | 3    | 15  | +------+-------+------+ SELECT * FROM `tbl1s_tbl2s` AS `Tbl1sTbl2` INNER JOIN (SELECT *, sum(Tbl2sbelong.`count`) as sum FROM `tbl2s` AS `Tbl2` INNER JOIN `tbl2sbelongs` AS `Tbl2sbelong` ON (`Tbl2`.`id`=`Tbl2sbelong`.`tbl2_id`) WHERE 1 = 1 GROUP BY `Tbl2`.`id` ) AS `SUB` ON (`Tbl1sTbl2`.`tbl2_id`=`SUB`.`id`) WHERE 1 = 1 GROUP BY `tbl1_id` を実行すると、 「SQL Error: 1060: Duplicate column name 'id' 」 というエラーが出てしまいます・・・ おそらくカラムのidが結合の中で重複しているという内容だと思うのですが、 3つもテーブルが絡んでくるとどれのidがというのが分からないのですが、 これは何が原因なのでしょうか? ちなみにサブクエリの SELECT *, sum(Tbl2sbelong.`count`) as sum FROM `tbl2s` AS `Tbl2` INNER JOIN `tbl2sbelongs` AS `Tbl2sbelong` ON (`Tbl2`.`id`=`Tbl2sbelong`.`tbl2_id`) WHERE 1 = 1 GROUP BY `Tbl2`.`id` この段階までは実行できます。 最終的には、「tbl2sbelongs」テーブルの「count」の値によって、「tbl1s」を降順に並べ替えたいと思っています。 この例だと テーブル「tbl1s」 +------+ |  id  | +------+ |  3  |count = tbl2_id「3」の15 = 15 +------+ |  1  |count = tbl2_id「1」の3 + tbl2_id「2」の10 = 13 +------+ |  2  |count = 0 +------+

  • MySQL
  • 回答数2
  • ありがとう数3

質問者が選んだベストアンサー

  • ベストアンサー
  • yambejp
  • ベストアンサー率51% (3827/7415)
回答No.1

こういうものは順序だてて考えればそんなに難しいものではありません。 (1)tbl1単位でcountを集計 SELECT tbl1_id,SUM(count) AS count FROM tbl1s_tbl2s INNER JOIN tbl2sbelongs USING(tbl2_id) GROUP BY tbl1_id (2)これをtbl1にLEFT JOIN SELECT id FROM tbl1s LEFT JOIN ( SELECT tbl1_id,SUM(count) AS count FROM tbl1s_tbl2s INNER JOIN tbl2sbelongs USING(tbl2_id) GROUP BY tbl1_id ) AS SUB ON tbl1s.id=tbl1_id ORDER BY count DESC

takagoo100
質問者

お礼

ご回答ありがとうございます。 そのやり方でできました。ありがとうございます。 質問ではtbl2sテーブルをJOINに絡めてましたが、後で気づいたのですがこれは必要なかったですね・・・ tbl2sbelongsテーブルとtbl1s_tbl2sで直接JOINできたんですね。 その後、 「SQL Error: 1060: Duplicate column name 'id' 」 のエラーが SELECT tbl1_id,SUM(count) を SELECT *,SUM(count) にしていたことが原因だったことが分かったのですが、 ということはINNER JOIN の段階(サブクエリの段階)では「*」でもエラーにならなかったってことは 次のLEFT JOINが原因なのかと思ってこちらもINNER JOINに変えたのですが、同じエラーでした・・・ 「*」にidも含まれてるからだとは思うのですが、これは一体どういうエラーなのでしょうか? サブクエリの段階(SELECT *, SUM(count) as count FROM `tbl1s_tbl2s` AS `Tbl1sTbl2` INNER JOIN `tbl2sbelongs` AS `Tbl2sbelong` ON (`Tbl1sTbl2`.`tbl2_id`=`Tbl2sbelong`.`tbl2_id`) WHERE 1 = 1 GROUP BY `tbl1_id`) ではtbl1s_tbl2s、tbl2sbelongs両方とも同じ名前のカラム「id」を所有していてもエラーが起きないのですが、 なぜ次のLEFT JOINした段階ではエラーが起こるのでしょうか?

その他の回答 (1)

  • yambejp
  • ベストアンサー率51% (3827/7415)
回答No.2

>なぜ次のLEFT JOINした段階ではエラーが起こるのでしょうか? ようは*を使うとエラーが検証しにくいということです。 きちんとコーディングする場合は*はまず使いません。 実際に個別に*の内容をみるとidが二つあったりするし、それを 結合するときに競合がでているように見受けられます

takagoo100
質問者

お礼

ご回答ありがとうございます。 つまり、はじめの2つの重複カラム(id)はmysql側でなんとか処理してくれるけど、 3つ目以降はエラーになるという認識でいいのでしょうか? とりあえず「*」は使わず取り出すように心がけることで対処していきたいと思います。

関連するQ&A

  • カーソルで値取得

    あるテーブルから頭から10件分 カーソルで値を取得するようにしていましたが、 元々下記のようだったものを… CURSOR cursor_name IS SELECT TBL_A.E_ID,TBL_A.C_ID FROM (SELECT E_ID,C_ID,ROW_NUMBER() OVER( ORDER BY E_ID ) RN  FROM TBL_A) TBL_A WHERE RN BETWEEN 1 AND 10;     ↓ CURSOR cursor_name IS SELECT TBL_A.E_ID, TBL_M.S_ID, TBL_M.S_NAME, TBL_U.USER_ID FROM ((TBL_A INNER JOIN TBL_EU ON TBL_A.E_ID = TBL_EU.E_ID) INNER JOIN TBL_U ON TBL_EU.S_ID = TBL_U.S_ID) INNER JOIN TBL_M ON TBL_EU.S_ID = TBL_M.S_ID WHERE (((TBL_EU.DIVISION)="2")); というように取得する値をふやしたいのですが、元にあった (SELECT E_ID,C_ID,ROW_NUMBER() OVER( ORDER BY E_ID ) RN  FROM TBL_A) TBL_A WHERE RN BETWEEN 1 AND 10; をどこに組み込んでいいのかわらず困っております。 どなかた教えて頂けないでしょうか?お願いいたします。

  • inner joinをすると数がおかしくなります

    SQLのinner joinについてお教え下さい。環境はWin 7 MYQL5です。 t1テーブルのデータ ID,在庫 001,22 t2テーブルのデータ ID,出庫 001,17 001,3 SELECT Sum(t1.stock) AS `在庫` FROM t1 where id = '001' 上記SQLの結果は22と表示されます。 SELECT Sum(t1.stock) AS `在庫` FROM t1 INNER JOIN t2 on t1.id = t2.id where id = '001' とやると、結果が44になってしまいます。 なぜそんな結果になってしまうのでしょうか? 結果はt1.stockは在庫22なので、22と表示するようにしたいです。 よろしくお願いいたします。

    • ベストアンサー
    • MySQL
  • group by句

    色々と試行錯誤してやっていますが、なかなか自分の 思うような結果が得られないためご質問させて下さい。 テーブルが全部で3つあります。 テーブルA id name 1 巨人 2   西武 テーブルB id name 1 小笠原 2 ラミレス 3 中島 4  片岡 テーブルC id テーブルAID テーブルBID 背番号 1 1 1 30 2 1 2 10 3 2 3 3 4 2 4 8 テーブルを結合し、テーブルCにある 背番号をテーブルAid,テーブルBidを元に sumしたいのですがうまくいきません。 以下がそのSQLになります。 (1)サブクエリーを使ったSQL この場合値が重複されて表示されてしまいます。 select a.name,b.name,c.name, (select sum(背番号) from tableC c where c.テーブルAId = a.id group by c.テーブルAid ), (select sum(背番号) from tableC c where c.テーブルBid = bid group by c.テーブルBid ) from tableC c inner join tableA a on a.id = c.テーブルAid inner join tableB b on b.id = c.テーブルBid (2) select a.name,b.name,c.name, (select sum(背番号) from tableC c where c.テーブルAId = a.id ), (select sum(背番号) from tableC c where c.テーブルBid = bid ) from tableC c inner join tableA a on a.id = c.テーブルAid inner join tableB b on b.id = c.テーブルBid group by c.テーブルAid 重複はされないのですが、group byが一つのみなので ちゃんとした出力がされません。    他にやり方があるのかもしれませんが、お分かりになる方が    いらっしゃいましたら、ご教授お願い致します。

  • 別テーブルのカラムを利用してソートしたい

    別テーブルのカラムを利用してソートしたい MySQLバージョン4.1.16を使用しています。 テーブル「tbl1」をテーブル「tbl2」のcountというカラムを利用して ソートしたいのですが、どのようなSQL文になるのでしょうか? 「tbl2」のidというカラムは外部キーで「tbl1」のidと関係しています。 テーブル「tbl1」 +------+---------+ |   id |  userid  | +------+---------+ |  1  | tanaka  | |  2  | sato   | +------+---------+ テーブル「tbl2」 +------+---------+ |   id |  count  | +------+---------+ |  1  |   10  | |  2  |   3   | +------+---------+ 次のような文かなと思ったのですが、エラーが返ってきます・・・ SELECT * FROM tbl1 ORDER BY (SELECT id FROM tbl2 ORDER BY count)

    • ベストアンサー
    • MySQL
  • 結合が上手くいきません

    以下のテーブルがあるとします table1 名前|住所コード|勤務地コード table2 コード|名称 テーブル1の検索結果にテーブル2の名称を引っ張ってきて取得したいのですがどうやるのでしょうか? SELECT * from table1 INNER JOIN table1.住所コード ON table2.コード INNER JOIN table1.勤務地コード ON table2.コード これではうまくいきませんでした。 SELECT (select 名称 from table2 where table2.コード=table1.住所コード),(select 名称 from table2 where table2.コード=table1.勤務地コード) FROM table1 これは上手くいくのですが重いらしいので、、、

    • ベストアンサー
    • MySQL
  • mySQLの内部結合について

    現在mySQLを使って、SQL文の勉強をしているのですがわからないことがあり、質問させていただきました。 テーブル同士をINNER JOINして結果を取得して、これに対してさらに別の処理(Whereなど)を行いたいのですが、うまくやり方がわかりません。 具体的にSQL文でいうとこんな感じです(ただしエラーが出て動きません)。 SELECT cmaster.comic_id,tags,title FROM mysql.comic_tag as ctag INNER JOIN mysql.comicmaster as cmaster ON ctag.comic_id = cmaster.comic_id AND WHERE tags = 'aa' この処理でやりたいことを説明するとcomic_tagとcomicmasterを結合して、その結果に対してさらにWhereでデータを絞るということしています。 このような場合はどのように処理をしたらいいんでしょうか?またjoinした後のデータを、既存のテーブルのように扱いたいのですが、なにか方法はないのでしょうか?

    • ベストアンサー
    • MySQL
  • 複数のテーブルの全てのカラムを一度に検索するには?

    検索対象のカラムがid(主キー)、bc1~bc40と41個あります。 1つのテーブルに41個のカラムを作り検索させると非常に時間がかかります。 それにインデックスを全部に付けたいですが16個までしかつけられないです。 なので、5つのテーブルにカラムを分けて全部のカラムにインデックスをつけて それぞれを検索させようと思っています。 テーブルが1つだけなら SELECT * FROM `bc` WHERE `bc1`='あいうえおかき' AND `bc2`='あいうえおかき' AND `bc3`='あいうえおかき' AND ・・・ `bc39`='あいうえおかき' AND `bc40`='あいうえおかき' ORDER BY `bc33` DESC LIMIT 0,50; のようにできますが、テーブルが複数の場合はどうしたらよいのでしょうか。 検索を試す前に下記ができるか試してみました。 SELECT COUNT(*) FROM (((`ccc` INNER JOIN `bbb` ON `ccc`.`id`=`bbb`.`id`) INNER JOIN `aaa` ON `ccc`.`id`=`aaa`.`id`) INNER JOIN `ddd` ON `ccc`.`id`=`ddd`.`id`) INNER JOIN `eee` ON `ccc`.`id`=`eee`.`id` エラーにはなりませんがカウント数が0になってしまいました。 SELECT COUNT(*) FROM (`ccc` INNER JOIN `bbb` ON `ccc`.`id`=`bbb`.`id`) INNER JOIN `aaa` ON `ccc`.`id`=`aaa`.`id` これは正確にできてカウント数100000 SELECT COUNT(*) FROM ((`ccc` INNER JOIN `bbb` ON `ccc`.`id`=`bbb`.`id`) INNER JOIN `aaa` ON `ccc`.`id`=`aaa`.`id`) INNER JOIN `ddd` ON `ccc`.`id`=`ddd`.`id` 4つ目のテーブルを入れたところから無理なようです。 他に良い方法はないのでしょうか。

    • ベストアンサー
    • MySQL
  • 複数JOINしているとCOUNTが正しく取得できな

    LAMP環境で開発をしています。 SQL文でCOUNTを求める際に、まとめて結果を求めようとして上手く行きません。 状況としては以下です。 テーブルdはidをkeyにa,b,c3つのテーブルとjoinしています。 id = 1の場合、テーブルa,b,cにマッチするレコードがそれぞれに4個、1個、0個あります。 ひとつひとつを SELECT COUNT(CASE WHEN a.name IS null THEN 1 ELSE null END) as a_count FROM d INNER JOIN a ON a.id = d.id WHERE d.id = 1 として結果を求めると4,1,0と出るのですが、まとめて SELECT COUNT(CASE WHEN a.name IS null THEN 1 ELSE null END) as a_count, COUNT(CASE WHEN b.name IS null THEN 1 ELSE null END) as b_count, COUNT(CASE WHEN c.name IS null THEN 1 ELSE null END) as c_count FROM d INNER JOIN a ON a.id = d.id INNER JOIN b ON b.id = d.id INNER JOIN c ON c.id = d.id WHERE d.id = 1 とすると28,5,0という値が返されます。 どのように書けば正しい4,1,0を得られるのでしょうか? よろしくお願いします。

    • ベストアンサー
    • MySQL
  • 3テーブルの外部結合

    3テーブルよりを以下の条件で1つのSELECT文で集計したいのですが可能でしょうか?  ・A_TBLのA単位でB_TBLのNYUKAとC_TBLのSYUKAを集計 <<A_TBL>>   <<B_TBL>>     <<C_TBL>> A  STOCK   B  A NYUKA   C  A SYUKA a01  100    b01 a02 10   c01 a03 10 a02  200    b02 a01 20   c02 a01 20 a03  300    b03 a01 10   c03 a05 10 a04  400    b04 a03 30   c04 a01 30 a05  500    b05 a05 30   c05 a03 20            b06 a02 20   c06 a01 10            b07 a01 10   c07 a03 50 外部結合 SELECT a.A,a.STOCK,SUM(b.NYUKA) AS SUM_NYUKA,SUM(c.SYUKA) AS SUM_SYUKA FROM A_TBL AS a". LEFT OUTER JOIN B_TBL AS b ON a.A=b.A LEFT OUTER JOIN C_TBL AS c ON a.A=c.A". GROUP BY a.A でうまくいきません。3つ以上のテーブルの外部結合の記述が間違っているのはわかるのですが、 どのように記述すればよいか、ネットで検索してもわかりませんでした。 宜しくお願い致します。

  • 結合と集計、同一のステートメント上だとエラーになる

    PostgreSQL初心者です。 結合と集計、別々のsqlステートメントだと動くのですが、同一のステートメントに記述するとエラーになります。 どなたか教えていただけると大変助かります。 phpPgAdmin を利用しております。 =エラーになったsqlステートメント= SELECT "pointm"."usercd", Sum("pointm"."getpoint"), "userm"."nickname" FROM "pointm" INNER JOIN "userm" on "pointm"."usercd" = "userm"."usercd" WHERE "pointm"."class" = '1' GROUP BY "pointm"."usercd"; =エラーメッセージ= ERROR: Attribute userm.nickname must be GROUPed or used in an aggregate function =動いた結合sql= SELECT "pointm"."usercd", "userm"."nickname" FROM "pointm" INNER JOIN "userm" on "pointm"."usercd" = "userm"."usercd" WHERE "pointm"."class" = '1'; =動いた集計sql= SELECT "pointm"."usercd", Sum("pointm"."getpoint") FROM "pointm" WHERE "pointm"."class" = '1' GROUP BY "pointm"."usercd";