我猜最初的问题是想找出如何从用户的输入中动态生成它,然后使用正确的 sql 参数来进行查询。
对于 sql 参数的使用,通常我所做的是使用通用辅助方法,一个快速示例(未测试):
public static class SqlHelpers
{
public static IEnumerable<T> ExecuteAdhocQuery<T>(SqlConnection con, string sql, CommandType cmdType, Func<SqlDataReader, T> converter, params SqlParameter[] args)
{
try
{
using (SqlCommand cmd = new SqlCommand(sql, con) { CommandType = cmdType })
{
cmd.Parameters.AddRange(args);
if (con.State != ConnectionState.Open) { con.Open(); }
var ret = new List<T>();
using (SqlDataReader rdr = cmd.ExecuteReader())
{
while (rdr.Read())
{
ret.Add(converter.Invoke(rdr));
}
}
return ret;
}
}
catch (Exception e)
{
// log error?
Console.WriteLine(e.Message);
Console.WriteLine(e.StackTrace);
throw e; // handle exception...
}
}
public void Test()
{
using (SqlConnection con = new SqlConnection("connection string here"))
{
var data = ExecuteAdhocQuery(con,
"SELECT ID, Name FROM tblMyTable WHERE ID = @Id and Status = @Status;",
CommandType.Text, (x) => new { Id = x.GetInt32(0), Name = x.GetString(1) },
new SqlParameter("@Id", SqlDbType.Int) { Value = 1 },
new SqlParameter("@Status", SqlDbType.Bit) { Value = true });
Console.WriteLine(data.Count());
}
}
}
当然,这只是阅读,对于插入/更新,也可以创建类似的方法。
但复杂的部分是如何在未知数量的条件以及它们之间的关系下使其动态化。所以一个快速的建议是使用委托方法或类来完成这项工作。样品(未测试):
public static Dictionary<string, SqlParameter> GetParamsFromInputString(string inputString)
{
var output = new Dictionary<string, SqlParameter>();
// use Regex to translate the input string (something like "[CookingTime] < 30 and [Cost] < 20" ) into a key value pair
// and then build sql parameter and return out
// The key will be the database field while the corresponding value is the sql param with value
return output;
}
public void TestWithInput(string condition)
{
var parameters = GetParamsFromInputString(condition);
// first build up the sql query:
var sql = "SELECT Id, Name from tblMyTable WHERE " + parameters.Select(m => string.Format("{0}={1}", m.Key, m.Value.ParameterName)).Aggregate((m,n) => m + " AND " + n);
using (SqlConnection con = new SqlConnection("connection string here"))
{
var data = ExecuteAdhocQuery(con,
sql,
CommandType.Text,
(x) => new { Id = x.GetInt32(0), Name = x.GetString(1) },
parameters.Select(m => m.Value).ToArray());
}
}
对于静态函数 GetParamsFromInputString,它只是一个示例。实际上,根据您的需要,它可能会非常复杂。
例如,您可能希望包含运算符(无论是 >、< 还是 <>、...)。
并且您可能还想包括条件之间的连词,无论是 AND 还是 OR。
如果它非常复杂,则构建委托类来完成这项工作。