当我为我的业务逻辑对象编写扩展方法时,我遇到了一个问题:如何更改转换方法的名称。someObject.ToAnotherObject()
与广泛使用的 object.ToString()
相似。
但是,例如LINQ混合使用这两种变体,我找不到它们之间的区别。 ToDictionary()
、ToList()
、AsParallel()
和 AsQueryable()
等方法都采用了这种命名方式。
这两种命名约定有什么区别,我应该知道什么来决定是否在自己的类中使用这种方式?
当我为我的业务逻辑对象编写扩展方法时,我遇到了一个问题:如何更改转换方法的名称。someObject.ToAnotherObject()
与广泛使用的 object.ToString()
相似。
但是,例如LINQ混合使用这两种变体,我找不到它们之间的区别。 ToDictionary()
、ToList()
、AsParallel()
和 AsQueryable()
等方法都采用了这种命名方式。
这两种命名约定有什么区别,我应该知道什么来决定是否在自己的类中使用这种方式?
ToDictionary
和 ToList
的前缀是 To
,因为它们不一定会保留原始集合的结构标识或其特性。
List<T>
转换为 Dictionary<K, V>
会创建一个具有全新结构的集合。HashSet<T>
转换为 List<T>
将移除集合的唯一性属性。带有 As
前缀的方法不会执行这些操作 - 它们只是提供原始集合的另一种 视图。它们丰富它。
ToXXX
方法会执行查询并从结果中创建一个新对象,而 AsXXX
方法则会生成一个不同的查询。它可能是相同的对象,但通过不同的接口访问(AsEnumerable()
这样做),或者它可能是修改功能的新对象(其他方法这样做,尽管有些方法会检查是否可以返回给定的对象,例如,如果源已实现 IQueryable<T>
,则 AsQueryable()
将返回 source
,否则将创建一个新的 EnumerableQuery<TElement>
)。ToXXX()
投影数据与原始数据没有关系。AsXXX()
保持与原始数据的活动关系(至少在我们讨论的 Enumerable/Queryable 示例中)。 - Tim M.ToXXX 执行查询
,而 AsXXX 生成新的查询
。从我在 LINQ 上阅读的内容来看,这听起来是正确的,而且 MSDN 似乎也证实了 ToXXX 的情况,但我想知道是否所有的 AsXXX
方法都是延迟执行的? - brichinsAsXXX
之上(例如 PLinq 添加的 AsParallel
,Entity Framework 提供的 AsNoTracking
等)。当然,Linq 的核心是由 Queryable
和 Enumerable
定义的,这两个类都遵循该约定。大多数附加功能也是如此,到了某种程度上,“所有”可能是正确的,但它太开放了,不能保证始终正确(尽管我认为任何破坏都是设计缺陷)。 - Jon Hanna
.AsCleanApple()
来表示我只需要清洗它,而调用.ToFruitSalad()
则意味着我的刀会改变苹果的结构吗? - PhysikbuddhaAsCleanApple
似乎会改变苹果的某些方面。更好的类比可能是AsFruit
。 - dcastro.AsCleanAppleSource()
的作用是将原本提供苹果的来源变成提供干净苹果的来源;如果需要,会添加清洗步骤,但如果已知苹果已经很干净了,则可能什么都不做。.ToPunnet()
则可以获取这个来源并为你提供一篮苹果。 - Jon Hanna