当您使用SqlDataReader时,返回集是由ExecuteReader步骤完全确定的,还是您可以通过在读取时写入源表来影响您获得的内容?这是一个非常粗略的伪代码示例。
sc = new SqlCommand("select * from people order by last, first",db) ;
sdr = sc.ExecuteReader() ;
while (sdr.read())
{
l = (string) sdr["last"] ;
k = (string) sdr["key"] ;
if (l.Equals("Adams"))
{
sc2 = new SqlCommand("update people set last = @nm where key = @key") ;
sc2.Parameters.Add(new SqlParameter("@nm", "Ziegler"));
sc2.Parameters.Add(new SqlParameter("@key", k));
sc2.ExecuteNonQuery() ;
}
}
我在其他环境中看到了很多因写入您正在阅读的表而导致的错误。这里记录k从列表顶部(Adams)到底部(Ziegler)。我假设(哈!)SqlDataReader是免疫的。真正?假
答案 0 :(得分:4)
这取决于您的transaction isolation level或其他锁定提示,但默认情况下,iirc从sql server中的表读取会锁定这些记录,因此您发布的代码将死锁(sc2最终会超时)或更新将进入事务日志,在读者完成之前不会写入任何内容。我不记得我的头顶。
答案 1 :(得分:1)
我看到的一个问题是,当阅读器处于打开状态时,它拥有数据库连接,在阅读器打开时没有其他任何东西可以使用它。因此,唯一可行的方法是使用不同的数据库连接,但仍取决于事务级别
答案 2 :(得分:0)
如果您想假设这些更新不会更改读取数据,您是否可以将数据读入临时对象容器,然后在完成所有读取后,然后执行更新?这会使问题没有实际意义。
当然,我确实从“这是如何运作”的立场中找到了有趣的问题。
答案 3 :(得分:0)
如果您想在迭代查询结果时进行更新,可以将其全部读入数据集。
我知道你没有问过这个,我也知道这是伪代码,但一定要把你的sc,sdr和sc2变量包装在using()语句中,以确保它们处理得当。< / p>