@IT会議室は、ITエンジニアに特化した質問・回答コミュニティ「QA@IT」に生まれ変わりました。ぜひご利用ください。
- PR -

可変する条件句

1
投稿者投稿内容
AIYON
会議室デビュー日: 2008/10/21
投稿数: 5
お住まい・勤務地: 新宿区西新宿
投稿日時: 2008-11-11 15:45
お世話になっております。
件名の通り、可変する条件句について悩んでおります。
というより、最善の方法が思い浮かびません。
参考までに、何かいい方法があればご教授をと願います。

使用環境:
VB6.0
SQLServer2005

基本流れ:
VB6.0から引数を渡し、SQLServer2005内のストアドで処理。
結果レコードセットをリターンします。

Vb6.0側画面:

条件列[ ] 条件記号[ ] 指定条件[ ]

SQL側テーブル:

│ID│発送数│年齢│ 性 │ 名 │
│1│ 10 │25│田中│太郎│
│2│ 8  │24│佐藤│一郎│
│3│ 9  │32│佐藤│花子│
│4│ 9  │38│中島│和子│
│5│ 5  │39│立花│次郎│
│6│ 3  │18│工藤│美和│
│7│ 4  │21│江藤│三郎│


条件列にはテーブルの列名「発送数」や「年齢」。
条件記号には「=」や「>」などが入ります。
指定条件には数値が入ります。

これを画面内でSQL文を作成せずに条件列、条件記号、指定条件の中身を
引数でストアドに渡し、ストアド内で処理をし下記のような結果を
返したいと思っています。

例:
@条件列=「発送数」
@条件記号=「>」
@条件=「5」

結果:
│ID│発送数│年齢│ 性 │ 名 │
│1│ 10 │25│田中│太郎│
│2│ 8  │24│佐藤│一郎│
│3│ 9  │32│佐藤│花子│
│4│ 9  │38│中島│和子│

よろしくお願い致します。
rain
ぬし
会議室デビュー日: 2006/10/19
投稿数: 549
投稿日時: 2008-11-11 16:04
ちょっと前に似たような質問を見かけた気がしたので、貼り。
http://www.atmarkit.co.jp/bbs/phpBB/viewtopic.php?topic=47009&forum=26&5

[ メッセージ編集済み 編集者: rain 編集日時 2008-11-11 16:05 ]
King
ぬし
会議室デビュー日: 2008/06/20
投稿数: 284
投稿日時: 2008-11-11 16:08
ストアド内で動的 SQL を使用してみてはどうでしょうか。
nakaP
大ベテラン
会議室デビュー日: 2005/09/27
投稿数: 138
お住まい・勤務地: 高知
投稿日時: 2008-11-11 16:12
動的SQLはどうでしょう・・・って遅かったかorz

なのでリンクだけ。
http://msdn.microsoft.com/ja-jp/library/ms188001(SQL.90).aspx
AIYON
会議室デビュー日: 2008/10/21
投稿数: 5
お住まい・勤務地: 新宿区西新宿
投稿日時: 2008-11-11 16:33
>>nakaP様
リンクありがとうございました。
サンプルと解説があったので助かりました!

>>King様
ストアド内でSETを使用して動的にSQL文を作るとは考えもしなかったです・・・。
ありがとうございます。試しに作ってみて実行してみます。

>>rain様
過去質問があったのですね。私の捜索不足でした。申し訳ございません。
リンクありがとうございました。当てはまる条件が少なければこれでもいけそうです。
この方法で作ってみて、条件句が長くなりそうなら、動的SQLにしようと思います。

ここからなんとか解決できると思うので、締させて頂きます。
ご解答くださった皆様ありがとうございました。
rain
ぬし
会議室デビュー日: 2006/10/19
投稿数: 549
投稿日時: 2008-11-11 16:53
引用:

AIYONさんの書き込み (2008-11-11 16:33) より:

>>rain様
過去質問があったのですね。私の捜索不足でした。申し訳ございません。
リンクありがとうございました。当てはまる条件が少なければこれでもいけそうです。
この方法で作ってみて、条件句が長くなりそうなら、動的SQLにしようと思います。


自分で引用しておいてアレですが、クエリのメンテナンスや性能を考えると、あまりお勧めはしません。動的SQLのほうがよいと思います。

また、条件に応じて複数のストアドプロシージャを用意することも、選択肢に入れてもらえればと思います。
メンテナンスという点では動的SQLに軍配が上がりますが、その反面、ストアドのメリットの1つである高速性が減ります。
何をもって最善とするかにもよりますので、要件に応じて選んでください。
ハニワ祭り
大ベテラン
会議室デビュー日: 2005/11/15
投稿数: 115
投稿日時: 2008-11-12 22:45
SQL本体はこんなかんじでいいのでは?
パラメータは上手く編集する感じで。

SELECT *
FROM テーブル
WHERE
ID BETWEEN ISNULL(@ID_MIN,0) AND ISNULL(@ID_MAX,9999)
AND 発送数 BETWEEN ISNULL(@発送数_MIN,0) AND ISNULL(@発送数_MAX,99999)
AND 年齢 BETWEEN ISNULL(@年齢_MIN,0) AND ISNULL(@年齢_MAX,200)
AND 性 LIKE '%' + @性 + '%'
AND 名 LIKE '%' + @名 + '%'
OPTION(RECOMPILE)


[ メッセージ編集済み 編集者: ハニワ祭り 編集日時 2008-11-12 22:51 ]
AIYON
会議室デビュー日: 2008/10/21
投稿数: 5
お住まい・勤務地: 新宿区西新宿
投稿日時: 2008-11-13 10:32
ハニワ祭り様
ご返信ありがとうございます。

BETWEENを使用する方法は私も考えたのですが
実際に業務で使用するテーブルでは変動する項目数が多く
また、その分のパラメータを増やすのも得策ではないと判断しました。
また条件記号の中には>=や<=の場合や>や<の場合もあるため
BETWEEN並びに<や>の記述は不適切かと思いました。
(記号の詳細を書かず申し訳ございませんでした。)

もっとも、はなっからこのような画面構成に問題あるのかもしれませんが・・・。


rain様

ご返信ありがとうございます。
結局、変動する項目数の多さを考慮して動的SQLを組むことにしました。

--■可変性演算式のため動的SQLで実行をかけます。
--WHERE句の作成
--条件列がNULLならWHERE句には空文字を挿入

CREATE Procedure TEST
(
@Invch条件列名 NVARCHAR(5)
@Invch条件式 NVARCHAR(10) --IS NOT NULL等も入ります
@Invch条件値 INT
)
AS

DECLARE @nvchSELECT  NVARCHAR(50)
DECLARE @nvchSQL NVARCHAR(100)
DECLARE @nvchWHERE NVARCHAR(30)

SET NOCOUNT ON

IF @Invch条件列名 IS NULL
 BEGIN
  SET @nvchWHERE = ''
 END
ELSE
 --NULLじゃなければ条件式作成。
 BEGIN
  --文字数が2以上なら、ISNULL か ISNOTNULL
  IF LEN(@Invch数値条件式) > 2
   BEGIN
    SET @nvchWHERE = ' WHERE (' + @Invch条件列名 + @Invch条件式 + ')'
   END
  ELSE
   BEGIN
    SET @nvchWHERE = ' WHERE (' + @Invch条件列名 + @Invch条件式
    SET @nvchWHERE = @nvchWHERE + CONVERT(VARCHAR,@Iint条件値) + ')'
   END 
 END

--SELECT句を作成します。
SET @nvchSELECT = 'SELECT * FROM TBテスト '

SET @nvchSQL = @nvchSELECT + @nvchWHERE

--SQL文の確認用
PRINT(@nvchSQL)

--実行
EXEC(@nvchSQL)

投稿時にサンプルで記入したテーブルを元にするとこのような感じでしょうか。
実際の業務で使用するのは定義した一時テーブルにINSERT EXECをしております。
おかげさまで、なんとかやりたいことを実現することができました。

ありがとうございました。



[ メッセージ編集済み 編集者: AIYON 編集日時 2008-11-13 10:45 ]
1

スキルアップ/キャリアアップ(JOB@IT)