アプリ版:「スタンプのみでお礼する」機能のリリースについて

SQL-Server2010を使用しています。
レコードを追加する際にキー項目が存在する場合は追加しないようなSQL文を作成しました。
追加するテーブルにレコードが1件以上あれば思ったとおりの処理となりますが、
1件も存在しない場合は追加できません。
下記がそのSQL文です。
原因と対策方法を教えて頂けませんでしょうか?

INSERT INTO foo(商品コード, 商品名)
SELECT DISTINCT 'ABC123' , 'りんご' FROM foo WHERE
NOT EXISTS(
SELECT * FROM foo WHERE 商品コード = 'ABC123' )

以上です。
宜しくお願い致します。

A 回答 (2件)

「SELECT 'ABC123' , 'りんご' FROM foo」と書くとfooのレコード数だけの行の('ABC123' , 'りんご')というデータを作成してしまいます。


質問の記述ではDISTINCTを用いてそれを再度一行にまとめようとしています。しかし、fooにそもそも一行もデータがないとまとめる段階でデータが存在しないので挿入できないのです。

また、fooのレコード数だけのレコードを作ってまとめるのは無駄な作業で、fooのレコード数が増加していくとパフォーマンスの劣化が見逃せなくなります。

SQLを記述する時は、「とりあえず、動けばいい」ではなく、どんな動作が裏で行われているかを念頭に置いておくようにしてください。

で、ACCESSですが、ACCESSの場合はFROM句を省略出来ません。
その代わりに何でもいいので一行のレコード(しかも一行のみ)のダミーテーブルを作成し、FROM句を構成すればいいのです。(OracleのDUAL表と一緒です)

フィールドも一つでバイト型で構いません。とりあえず「0」の値を入力しておけば結構です。テーブル名も「DUAL」とでもつけてください。

そうすれば
INSERT INTO foo(商品コード, 商品名)
SELECT DISTINCT 'ABC123' , 'りんご' FROM DUAL
WHERE NOT EXISTS(
SELECT * FROM foo WHERE 商品コード = 'ABC123' )

でいけるはずです。
    • good
    • 0
この回答へのお礼

分かりやすい説明ありがとうございます。大変良く理解できました!
ACCESSでDUALテーブルを作成し1レコードだけ作成した結果、実現できました!
今日半日以上この件で試行錯誤し悩んでおりましたので感激です。
有難う御座いました。

お礼日時:2011/04/27 18:55

「SELECT DISTINCT 'ABC123' , 'りんご' FROM foo」の「FROM foo」が悪さしてます。


これを付加した意図はなんでしょう?

INSERT INTO foo(商品コード, 商品名)
SELECT 'ABC123' , 'りんご'
WHERE NOT EXISTS(
SELECT * FROM foo WHERE 商品コード = 'ABC123' )

ではダメですか?

この回答への補足

回答ありがとうございます。
早速SQL-Serverで試してみたところ思ったとおりの動きになりました。
SELECT句とFROM句はセットで使用するものと思っていたのが間違いでした。

再度質問になるのですが、
同じことをAccess2003でも実現したいのですが、Access2003では「構文エラー」と
なってしまいます。
どのような解決方法がありますでしょうか?
宜しくお願い致します。

補足日時:2011/04/27 18:12
    • good
    • 0

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!