1

ASP.NET 4.0、Web フォーム、C#、SQL

出会い系サイトで見かける検索フォームによく似たものがあります。複数のドロップダウン ボックス、および各 ddbox には特定の値と「任意の」値があります。ボタン クリック イベントの背後にある C# のコードで多くの else if ステートメントを使用して、以下の例の外でこの構文を作成する簡単な方法は考えられません。

if
= && = && =
else if<br/>
= && = && !=
else if<br/>
= && != && != 
else if<br/>
!= && = && !=

... これは、選択された値を持つ同じシーケンスです

if
Any && Any && Any
else if
Any && Any && Not Any
else if
Any && Not Any && Not Any
else if
Not Any && Any && Not Any

これは、すべてのシナリオを循環するまで続きます。ボタンをクリックすると、コードビハインドが選択された値を取得し、実行するクエリを決定します。頭痛の原因と思われるのは、ddbox の値「any」です。c# または sql 構文を構造化して、else if の数を減らすための推奨される方法はありますか?

これが理にかなっている場合、またはさらに情報が必要な場合はお知らせください。

4

2 に答える 2

2

私は次のように書きます:

create procedure usp_search (
    @param1 varchar(50) = null
   ,@param2 carchar(50) = null
) as
begin
    select field1
          ,field2
          ,field3
          ,fieldN
      from table t with(nolock)
     where ((@param1 is null) or (t.fieldX == @param1))
       and ((@param2 is null) or (t.fieldY == @param2))
end

それからあなたのクライアントであなたは好きです

//code
var connection = new SqlConnection("connection_string");
var command = new SqlCommand();
command.Connection = connection;
command.CommandText = "usp_Search";
command.CommandType = CommandType.StoredProcedure;
if((string.IsNullOrEmpty(stringVariable1)) || (stringVariable2.ToLower().Equals("any"))) {
    command.Parameters.Add("@param1", SqlType.VarChar, 50).Value = DBNull.Value;
} else {
    command.Parameters.Add("@param1", SqlType.VarChar, 50).Value = stringVariable1;
}
if((string.IsNullOrEmpty(stringVariable2)) || (stringVariable2.ToLower().Equals("any"))) {
    command.Parameters.Add("@param2", SqlType.VarChar, 50).Value = DBNull.Value;
} else {
    command.Parameters.Add("@param2", SqlType.VarChar, 50).Value = stringVariable2;
}
// code

これらの行に沿ったもの...このようにして、検索クエリはフィルタリングされた結果またはフィルタリングされていない結果を取得できます..もちろん、このタイプのクエリのいくつかの落とし穴に注意する必要があります

編集: C# コードでのみ行われる同じことは、次のようになります。

var sb = new StringBuilder();
sb.Append("select field1 ,field2, field3, fieldN ");
sb.Append("from table t with(nolock) ");
sb.Append("where ((@param1 is null) or (t.fieldX == @param1))");
sb.Append("and ((@param2 is null) or (t.fieldY == @param2))");

var connection = new SqlConnection("connection_string");
var command = new SqlCommand();
command.Connection = connection;
command.CommandText = sb.ToString();
command.CommandType = CommandType.Text;
if((string.IsNullOrEmpty(stringVariable1)) || (stringVariable2.ToLower().Equals("any"))) {
    command.Parameters.Add("@param1", SqlType.VarChar, 50).Value = DBNull.Value;
} else {
    command.Parameters.Add("@param1", SqlType.VarChar, 50).Value = stringVariable1;
}
if((string.IsNullOrEmpty(stringVariable2)) || (stringVariable2.ToLower().Equals("any"))) {
    command.Parameters.Add("@param2", SqlType.VarChar, 50).Value = DBNull.Value;
} else {
    command.Parameters.Add("@param2", SqlType.VarChar, 50).Value = stringVariable2;
}
于 2012-04-18T23:24:35.160 に答える
0

最初に、次のプロジェクトで ORM を使用することを検討することをお勧めします。動的 SQL には、アプリケーションの設計に関して、この種の注意事項がたくさんあるからです。

とはいえ、これを処理した方法は、オプションの検索語を括弧内に配置することでした。これにより、次のことが可能になりました。

(SomeField = 'Blah' OR 1=1)

これが良い解決策だと言っているわけではありませんが、SQL ステートメントを順番に作成できるため、ネストされたステートメントの数を減らすことができます。

次のコードを検討してください。

SQL = "SELECT CompanyName, CompanyState FROM Companies WHERE ";
SQL += "(CompanyName = '" & CompanyName & "' " + (CompanyName == "AnyKey" ? " OR 1=1" : "") + ") ";
SQL += "(CompanyState = '" & CompanyState & "' " + (CompanyState == "AnyKey" ? " OR 1=1" : "") + ") ";

繰り返しますが、これは良いと見なされるべきではないことを強調します。それ以来、ORMに移行したので、この問題はもうありません。そしていつものように、ユーザー入力をサニタイズしてください。

お役に立てれば。

于 2012-04-18T23:23:39.873 に答える