Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 单例工厂成员函数线程安全_C#_Multithreading_Singleton_Thread Safety_Factory - Fatal编程技术网

C# 单例工厂成员函数线程安全

C# 单例工厂成员函数线程安全,c#,multithreading,singleton,thread-safety,factory,C#,Multithreading,Singleton,Thread Safety,Factory,我想要一个生成IPropertyMapper对象的单例工厂。工厂有一个字典,其中包含对Func委托的引用。字典是不可变的,我只想快速访问。下面的代码是线程安全的吗?调用Create()是否线程安全 类别定义: public sealed class PropertyMapperFactory { private static readonly PropertyMapperFactory _instance = new PropertyMapperFactory();

我想要一个生成IPropertyMapper对象的单例工厂。工厂有一个字典,其中包含对Func委托的引用。字典是不可变的,我只想快速访问。下面的代码是线程安全的吗?调用Create()是否线程安全

类别定义:

public sealed class PropertyMapperFactory
    {
        private static readonly PropertyMapperFactory _instance = new PropertyMapperFactory();

        private readonly Dictionary<int, Func<TResult>> _handlers;

        private PropertyMapperFactory() {
            this._handlers = new Dictionary<...>();
            this._setTimeHandler();
        }

        public static PropertyMapperFactory GetFactory() {
            return _instance;
        }

        //Is this thread safe?
        public IPropertyMapper Create(UnitSetting _units ) {
            return new PropertyMapper(this.handler[0])
        }            
公共密封类PropertyMapperFactory
{
私有静态只读PropertyMapperFactory _实例=新PropertyMapperFactory();
专用只读字典处理程序;
私人物业制造商(){
这是。_handlers=new Dictionary();
这是。_setTimeHandler();
}
公共静态属性MapperFactory GetFactory(){
返回_实例;
}
//这个线安全吗?
公共IPropertyMapper创建(单位设置_单位){
返回新的PropertyMapper(此.handler[0])
}            

通常认为从并发线程读取
字典类型是安全的,但所有写入操作必须完全隔离(不能同时进行其他写入或读取)。如果在构造后的任何时候都不修改字典,则应该可以。

字典类型通常被认为是从并发线程读取的安全类型,但所有写入操作必须完全隔离(没有其他写入操作或读取操作同时进行)。如果您在构造后的任何时候都不修改字典,那么应该可以。

假设您在构造函数完成后从未更改字典中的值,这很好。
字典支持多个读取器,只要没有任何写入程序。

假设您从未更改字典中的值a在构造函数完成后重试,这很好。
Dictionary
支持多个读卡器,只要没有任何写卡器。

嘿,亚当,谢谢你的回答。我的委托函数定义如下:Func((target)=>{return target.toString()});。我的委托是否也将在当前线程堆栈上执行?因为这是一个共享变量/函数ptr,它是否需要同步原语?@Amit:如果您有单独的无关问题,请发布单独的问题。不要在注释中问无关的问题。@Timwi:嘿,Tim,它们与我的解决方案相关。我将继续我的qu路线在线程安全的前提下,使用保存委托哈希的单例进行测试。上面的代码可能不会传递它,但对处理程序[0]的引用在PropertyManager中设置,然后由调用单例的Create()函数的线程使用。@Amit:调用委托没有什么不同(从调用堆栈的角度)而不是调用任何其他函数。如果您使用
invoke
函数调用它(或仅通过将paren附加到变量末尾并直接调用它),那么它将在当前调用堆栈上运行,就像任何其他函数一样。如果您使用
BeginInvoke
调用它,它将(可能,但不一定)使用
ThreadPool
进行调用,这样它将位于不同的线程上。嘿,亚当,谢谢你的回答。我的委托函数定义如下:Func((target)=>{return target.toString()});。我的委托是否也将在当前线程堆栈上执行?因为这是一个共享变量/函数ptr,它是否需要同步原语?@Amit:如果您有单独的无关问题,请发布单独的问题。不要在注释中问无关的问题。@Timwi:嘿,Tim,它们与我的解决方案相关。我将继续我的qu路线在线程安全的前提下,使用保存委托哈希的单例进行测试。上面的代码可能不会传递它,但对处理程序[0]的引用在PropertyManager中设置,然后由调用单例的Create()函数的线程使用。@Amit:调用委托没有什么不同(从调用堆栈的角度)而不是调用任何其他函数。如果您使用
invoke
函数调用它(或仅通过将paren附加到变量末尾并直接调用它),那么它将在当前调用堆栈上运行,就像任何其他函数一样。如果您使用
BeginInvoke
调用它,它将(可能,但不一定)使用
ThreadPool
进行调用,使其位于不同的线程上。