我在SQL Server数据库中有这个表MyTable(简化):
我需要为status
等于1且status
小于当前时间的所有行更新expires
。
出于测试目的,MyTable中有一个条目:[id = 1,status = 1,expires ='2017.08.25。 21:17:28',notes ='bla bla bla']
这是我正在使用的代码:
linqTable.Where(r => r.status == 1 &&
r.expires != null &&
r.expires < DateTime.Now)
.ToList()
.ForEach(r => r.status = 7);
db.SubmitChanges();
我偶然发现了db.SubmitChanges()
上的令人费解的错误:
数据类型ntext和nvarchar在等于运算符
中不兼容
启用SQL语句日志记录显示了幕后发生的事情:
UPDATE [dbo].[MyTable]
SET [status] = @p4
WHERE ([id] = @p0) AND ([status] = @p1) AND ([expires] = @p2) AND ([notes] = @p3)
-- @p0: Input Int (Size = -1; Prec = 0; Scale = 0) [1]
-- @p1: Input Int (Size = -1; Prec = 0; Scale = 0) [1]
-- @p2: Input DateTime (Size = -1; Prec = 0; Scale = 0) [2017.08.25. 21:17:28]
-- @p3: Input NVarChar (Size = 4000; Prec = 0; Scale = 0) [bla bla bla]
-- @p4: Input Int (Size = -1; Prec = 0; Scale = 0) [7]
原因是错误的原因是ntext
列的类型不正确。但这不是真正的问题。 LINQ生成的SQL语句效率很低:
它通过查询所有列来选择记录,什么是废话,只使用主键列就足够了!我已声明id
是主键列
我必须只为一个列更新多个记录。单个记录应该没有更新
我期待这样的查询:
UPDATE [dbo].MyTable
SET [status] = @p1
WHERE status = @p0 AND expires IS NOT NULL AND expires < GETDATE()
-- @p0: 1
-- @p1: 7
是否有可能实现如此高效的SQL语句生成?
答案 0 :(得分:0)
嗯,Linq-2-sql中没有(开箱即用)批量更新。有一些实现,如 https://terryaney.wordpress.com/2008/04/14/batch-updates-and-deletes-with-linq-to-sql/
&#34;它通过查询所有列来选择记录,什么是废话,只使用主键列就足够了#34;
- &GT;我认为这不会对效率产生很大影响。这是每个记录的更新是昂贵的