为什么 CancellationToken 是一个结构?

Why CancellationToken is a struct?

在 CancellationToken 的情况下使用结构而不是引用类型是否有意义?

我看到一个可能的缺点,当我将它作为参数传递时,它会在方法链中一直复制下去。

同时,对于struct来说,分配和释放的速度可能会更快。

如果我们想让它不可变,我们可以使用只读属性或私有设置器。

那么它背后的想法是什么?

Does it make any sense to use a struct instead of a reference type in case of CancellationToken?

是的。

I see one possible disadvantage, it will be copied all the way down in methods chain as I pass it as a parameter.

这不是劣势。取消令牌是参考大小的。为什么传递引用大小的结构与传递引用相比会有缺点?这种反对没有意义。请解释为什么您认为这是 "disadvantage".

In the same time, as far as it is struct, it might be allocated and disposed faster.

这是正确的,但实际的胜利更有可能是一个包含引用的引用大小的结构不会增加收集压力。 .NET Framework 中的许多设计和实现决策旨在确保收集压力不会因框架代码而增加太多。

So what was an idea behind it?

这是一个逻辑上是值的小类型;为什么不应该它是一个值类型?

有一篇文章介绍了 .NET 取消设计 here,值得一读。关于您的问题,评论中提出以下问题:

Just out of interest, why is the CancellationToken a value type?

并且提问者提出了一个替代实现,使用 CancellationToken 的单个共享实例作为引用类型。

Mike Liddell 的回复:

This would certainly work and is largely equivalent (and we implemented it this way during early prototyping), but we went with the current design for two particular reasons:

– only one class instance per CTS/Token, hence less GC pressure.

– we consolidate all of the state and most of the logic onto CTS. The split arrangement was a somewhat more convoluted.

我会注意到当前的值类型实现与引用的大小完全相同,因此没有任何额外的复制开销。它还可以防止在用户代码中进行一些额外的样板空检查,尤其是在将令牌设置为可选参数时。