c# - 可查询的 WHERE 包含 String、Int、DateTime

标签 c# sql iqueryable

我正在处理这行代码:

query = query.Where(p => 
  p.ChckNumber.ToString().Contains(globalSearch.ToString()) || 
  p.BankAccount.ToString().Contains(globalSearch.ToString()) || 
  p.Description.ToString().Contains(globalSearch.ToString()) || 
  p.CheckAmount.ToString().Contains(globalSearch) || 
  p.ClearedDate.ToString().Contains(globalSearch.ToString()) || 
  p.SentDate.ToString().Contains(globalSearch.ToString()));

通过这行代码,我基本上是在进行搜索,当 globalSearch 是一个 string 并且像 BankAccount 这样的列时,它似乎工作正常> 和 Descriptionvarchar,但是,当 globalSearchIntDateTime 时(-2233 或 4/9/2013)对于 CheckAmount (int)ClearedDate (DateTime)SentDate (DateTime) 列,它返回 0 行,如果 globalSearch 匹配 ChckNumber 中的 int 它有效!

我做错了什么?

我在 SQL Server 中运行了这个查询:

SELECT CONVERT(VARCHAR(MAX), ClearedDate) FROM myTable

我所有的日期都返回 Sep 9 2017 如果 globalSearch 是 Sep 10 2017 它有效,但它不适用于我需要的格式:9/9/2017

最佳答案

您不应该关心 globalSearch 是否是 Int,因为您应该始终将它转换为字符串,除非是 DateTime,并且您不应该关心列是 varchar 还是 Int,因为您总是将列转换为字符串,除非 DateTime .

请注意,根据您的评论,我假设您只比较月、日和年,并不关心 ClearedDate 的时间

我发现您的代码存在三个潜在问题:

  1. 您没有将 globalSearch 转换为 CheckAmount 列的字符串
  2. 在调用 .ToString 之前您不检查任何列的空值,也许您的所有列都不允许空值
  3. 您的代码可读性不佳,人眼很难发现不一致之处。

这里是每次都将 globalSearch 转换为字符串的更具可读性的代码,因为同样,您不会将 globalSearch 转换为 CheckAmount 的字符串:

var gsStr = globalSearch.ToString();
var gsDate = DateTime.MinDate;
if(globalSearch.GetType() == typeof(DateTime))
{
    gsDate = globalSearch;
}
query = query.Where(p => p.ChckNumber.ToString().Contains(gsStr) 
|| p.BankAccount.ToString().Contains(gsStr) 
|| p.Description.ToString().Contains(gsStr) 
|| p.CheckAmount.ToString().Contains(gsStr) 
|| p.ClearedDate.Date == gsDate.Date
|| p.SentDate.ToString().Contains(gsStr));

如果您使用的是 C# 6.0,则可以使用新的 Null Propagation Operator 来防止在您的任何列现在或将来允许 null 时发生错误:

var gsStr = globalSearch.ToString();
var gsDate = DateTime.MinDate;
if(globalSearch.GetType() == typeof(DateTime))
{
    gsDate = globalSearch;
}
query = query.Where(p => p.ChckNumber?.ToString().Contains(gsStr) 
|| p.BankAccount?.ToString().Contains(gsStr) 
|| p.Description?.ToString().Contains(gsStr) 
|| p.CheckAmount?.ToString().Contains(gsStr) 
|| p.ClearedDate?.Date == gsDate.Date
|| p.SentDate?.ToString().Contains(gsStr));

将 globalSearch ToString 转换为 CheckAmount Contains 可能会解决您的问题,使您的代码更具可读性并防止出现空值,如果它不修复错误,则更容易调试。

关于c# - 可查询的 WHERE 包含 String、Int、DateTime,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42561321/

相关文章:

c# - Unity 的 GetComponent 通过字符串(或通过从另一个脚本传递的其他方法)

c# - 在 ApiController 中添加自定义响应 header

mysql - Doctrine 1.2 : get products where associated simple products have stock

c# - 使用 C# 打开 excel 实例

mysql - MySQL 中组的最新条目

python - 是否可以将约束 unique = True 除了空字符串设置到 SQLAlchemy 中?

c# - 动态构建 IQueryable OR 语句

asp.net-mvc-3 - 为什么将Count与IQueryable一起使用被认为是不可行的

c# - 找不到 ExpressionVisitor.VisistMemberAcess

C# Linq to CSV 动态对象运行时列名称