gpt4 book ai didi

c# - 使用静态 MemcachedClient 的问题

转载 作者:行者123 更新时间:2023-11-30 12:22:41 26 4
gpt4 key购买 nike

我正在使用 Memcached 存储数据以便快速访问。我读到创建 MemcachedClient 的成本很高,并且看到 MemcachedClient 的用法是静态的(参见:link)

所以我为我的客户使用单例模式:

public class CommonObjectsCache
{
private static CommonObjectsCache _cache;
private static MemcachedClient _client;

public static MemcachedClient Client
{
get
{
if (_client == null)
_client = new MemcachedClient();

return _client;
}
private set
{
_client = value;
}
}

private CommonObjectsCache()
{
_client = new MemcachedClient();
}

public static CommonObjectsCache Cache
{
get
{
if (_cache == null)
_cache = new CommonObjectsCache();

return _cache;
}
}
}

在我的 DAL 中,我按如下方式使用它们:

    public static List<Item1> AllItem1s
{
get
{
if (CommonObjectsCache.Client.Get<List<Item1>>("AllItem1s") == null)
RefreshItem1Cache();

return CommonObjectsCache.Client.Get<List<Item1>>("AllItem1s");
}
private set
{
CommonObjectsCache.Client.Store(StoreMode.Set, "AllItem1s", value);
}
}
public static List<Item2> AllItem2s
{
get { // Same as above }
private set { // Same as above }
}
public static List<Item3> AllItem3s
{
get { // Same as above }
private set { // Same as above }
}
public static List<Item4> AllItem4s
{
get { // Same as above }
private set { // Same as above }

}

并将它们填写为:

public static void RefreshItem1Cache()
{
List<Item1> items = (from i ctx.Item1
select i).ToList();
AllItem1s = items;
}

在我的 DAL 代码中,我有一个类似的方法:

public static MyModel GetMyModel(int? id)
{
// I use AllItem1s here.
}

当我运行代码时,它有时会显示 AllItem1s.Count == 0,但是当我在 AllItem1s 中设置断点并诊断该值时,我发现它已被填充。因此,我按如下方式更新了代码以检查我是否做错了:

public static MyModel GetMyModel(int? id)
{
if (AllItem1s == null || AllItem1s.Count == 0 || AllItem2s == null || AllItem2s.Count == 0 || AllItem3s == null || AllItem3s.Count == 0 || AllItem4s == null || AllItem4s.Count == 0)
{
string msg = "Error!!!!!";
}
// I use AllItem1s here.
}

令人惊讶的是,代码落在string msg = "Error!!!!!"; block !!!

但是当我在 if block 中放置一个断点并观察每个集合的 Count 属性时,我看到它们有数字。

所以我得出结论,在获取 AllItemXs 属性时存在竞争条件。当它检查条件时,至少有一个没有被正确设置(这没有意义,因为它们在同一个线程上,并且属性的 getter 不能返回空集合)。

谁能解释为什么会发生这种情况以及如何解决这个问题?

最佳答案

您的单例实现不是线程安全的。想象一下,两个(或更多)线程同时命中空检查:两个(所有)线程都将初始化它们自己的 CommonObjectsCache 实例。

您可以使用 lock 语句包装实例的空检查和初始化,或者使用双重检查锁定模式。

只需在 google 上搜索 C# 中的线程安全单例实现。

关于c# - 使用静态 MemcachedClient 的问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40132483/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com