我正在开发一个C#库,它将创建大量小对象作为正常操作的一部分(想想编译器中的AST节点)。我想以一种不会妨碍性能的方式为每个实例分配一个唯一的标识符(在程序中是唯一的,而不是全局唯一的)。这些对象是不可变的,并且可以跨线程共享,因此id必须在线程中是唯一的。
以下是我正在考虑的一些选项:
Interlocked.Increment()
Guid.NewGuid()
生成ID [ThreadStatic]
属性的静态int或long字段,然后从当前线程的ManagedThreadId
属性和线程本地计数器中的下一个值创建一个字符串id。其中一个会比其他人更高效吗?有更好的方法吗?
谢谢!
编辑:
我跑了一个快速的基准测试并得到了以下结果:
这似乎强烈倾向于使用Interlocked
。但是,在多线程场景中是否存在Interlocked
减速的风险?
答案 0 :(得分:1)
Interlocked.Increment
通过确保对++
的调用作为原子操作发生来工作。这意味着另一个线程无法获取中间变量,这可能会使用++
发生。
唯一的性能问题是需要同步存储变量的内存,请注意,这个性能成本应该可以忽略不计,正如您的测试似乎显示的那样。