|
|
1
33
如果基础数据存储为列表,则可以使用
List(T).AsReadOnly
|
|
|
2
19
但是,如果您的目的是防止调用代码观察来自其他线程的更新,那么您必须退回到前面提到的解决方案,根据需要执行深度或浅层复制。 |
|
|
3
19
我投票赞成你的回答,同意这一点,但我能给你一些考虑吗? 不要直接返回集合。创建一个准确命名的业务逻辑类,该类反映集合的目的。 这样做的主要优点在于,您无法向集合添加代码,因此,每当您的对象模型中有一个本机“集合”时,您总是可以在整个项目中使用非OO支持代码来访问它。 例如,如果您的集合是发票,那么代码中可能有3到4个地方可以迭代未付发票。您可以有一个getUnpaid方法。然而,当你开始考虑像“支付发票(付款人,账户)”这样的方法时,真正的力量就来了。 当您传递集合而不是编写对象模型时,您将永远不会遇到整个重构类。 还要注意的是,这让你的问题变得特别好。如果您不希望人们更改集合,那么您的容器不需要包含任何变体。如果您以后决定在一种情况下您实际上必须修改它,那么您可以创建一个安全的机制来进行修改。
|
|
|
4
11
我认为你在这里混淆了概念。
这个
-如果您不关心调用方(类B)看到集合的任何进一步更改,那么您可以克隆集合,分发它,然后停止关心。 -如果您确实需要调用方(类B)来查看对集合所做的更改,并且希望这是线程安全的,那么您将面临更多的问题。一种可能是实现您自己的ReadOnlyCollection线程安全变体,以允许锁定访问,但如果您想支持IEnumerable,这将是非常重要且不具性能的,并且 不会保护您免受集合中可变元素的影响。 |
|
|
5
3
aku 的答案只会将列表保护为只读。列表中的元素仍然非常可写。我不知道在将非原子元素放入只读列表之前,是否有任何方法可以在不克隆它们的情况下保护它们。 |
|
|
6
3
你想使用 yield 关键词。在IEnumerable列表中循环,并使用yeild返回结果。这允许消费者使用for each,而无需修改集合。 它看起来像这样:
|
|
|
7
2
您可以改为使用集合的副本。
这样一来,它是否得到更新并不重要。 |