我使用以下代码缓存"People“表的"Name”列的更改。但是,在一行中,如果其他列(如Address列)发生更改,则还会触发和清除缓存。(ASP.NET 4.0与Server 2008。)
public string GetTheVals()
{
string vals = HttpContext.Current.Cache["TheCacheKey__X"] as string;
if (vals == null)
{
con = GetConnection();
SqlCommand cmd = new SqlCommand(@"
SELECT Name
FROM dbo.People
", con);
con.Open();
SqlCacheDependency sqlDependency = new SqlCacheDependency(cmd);
SqlDataReader rdr = null;
StringBuilder builder = new StringBuilder("");
rdr = cmd.ExecuteReader();
while (rdr.Read())
{
builder.Append(rdr[0].ToString());
}
vals = builder.ToString();
HttpContext.Current.Cache.Insert("TheCacheKey__X", vals, sqlDependency, System.Web.Caching.Cache.NoAbsoluteExpiration, TimeSpan.FromMinutes(20));
CloseConnection(con);
}
return vals;
}为什么当一个列的值(在命令的查询中不存在)发生变化时会触发它,尽管据说在结果发生变化时会触发它?
还可以将委托分配给OnChange事件,当相关命令的结果发生变化时,该事件将触发。 http://msdn.microsoft.com/en-us/library/62xk7953.aspx
它还需要显式地声明列,因此我们理解它将过滤掉表中的其他列,而不会触发。
SELECT语句中的投影列必须显式声明,表名必须限定为两个部分的名称。注意,这意味着语句中引用的所有表都必须位于同一个数据库中。 语句不能使用星号(*)或table_name.*语法来指定列。 该语句不得包含子查询、外部联接或自联接。 http://msdn.microsoft.com/en-us/library/ms181122(v=sql.105).aspx
发布于 2012-10-25 08:16:27
然而,根据女士帮助的说法:
当发生下列事件之一时,Server将发送订阅的查询通知:
请注意,Server 可能会针对不更改数据的事件产生查询通知,或者响应不实际影响查询结果的更改。例如,当UPDATE语句更改查询返回的一行时,即使对该行的更新没有更改查询结果中的列,通知也可能触发。
发布于 2012-10-25 08:24:55
当我使用SQL依赖项时,我注意到了许多您应该考虑的问题。
其中之一,您不能缓存一个表取决于列名,如果您想看到您的缓存表打开AspNet_SqlCacheTablesForChangeNotification在您的数据库。
从dbo.AspNet_SqlCacheTablesForChangeNotification中选择TOP 1000 tableName、notificationCreated、changeId
您将注意到何时会触发changeId,在更新、插入或删除时,这将触发要刷新的缓存。
非常重要的是,要始终检查命令通知中的查询,许多查询都不受支持,正如您前面所说的。
希望它能帮上忙。
https://stackoverflow.com/questions/12705454
复制相似问题