我的代码充满了集合-我想这不是一件不寻常的事情。但是,各种集合类型的用法并不明显也不是琐碎的。通常,我想使用公开“最佳” API且语法噪音最少的类型。 (有关可比的问题,请参见Best practice when returning an array of valuesUsing list arrays - Best practices)。有一些指南建议在API 中使用哪种类型,但是在常规(非API)代码中,这是不切实际的。

例如:

new ReadOnlyCollection<Tuple<string,int>>(
    new List<Tuple<string,int>> {
        Tuple.Create("abc",3),
        Tuple.Create("def",37)
    }
)
List是一个非常常见的数据结构,但是以这种方式创建它们会涉及很多语法噪声-并且很容易变得更糟(例如字典)。事实证明,许多列表从未更改,或者至少从未扩展。当然ReadOnlyCollection引入了更多的语法噪音,甚至没有传达我的意思。毕竟ReadOnlyCollection可以包装一个变异集合。有时我在内部使用数组,然后返回IEnumerable表示意图。但是这些方法大多数都具有非常低的信噪比。这对于理解代码至关重要。

对于不是公共(public)API的所有代码中的99%,没有必要遵循框架准则:但是,我仍然想要可理解的代码和能传达意图的类型。

那么,处理沼泽标准任务(使小型集合传递值)的最佳实践方法是什么? 是否应该在可能的情况下使用数组而不是List?还有其他东西吗?传递如此小的收藏集的最佳方法-干净,可读,合理有效-是什么?特别是,对于尚未阅读此问题并且不想阅读大量API文档但仍然了解其意图的 future 维护者,代码应该是明显的最小化代码困惑也是非常重要的-因此ReadOnlyCollection之类的东西充其量是可疑的。对于具有较小表面的主要API,罗types类型没有错,但作为大型代码库中的常规做法,这没有错。

在没有大量代码困惑(例如显式类型参数)的情况下传递值列表的最佳方法是什么,但仍然可以清楚地传达意图?

编辑:阐明这是关于编写简短的代码,而不是关于公共(public)API。

最佳答案

更新:

因此,严格来讲,这并不是新事物。但是这个问题使我相信go ahead and announce an open source project I've had in the works for a while(仍在进行中,但是里面还有一些有用的东西),其中包括IArray<T>接口(interface)(以及实现方式,自然而然),我认为它完全可以捕获您想要的内容:索引,已读,仅,甚至协变(bonus!)接口(interface)

一些好处:

  • 这不是像ReadOnlyCollection<T>这样的具体类型,因此不会将您束缚于特定的实现。
  • 它不仅是包装器(如ReadOnlyCollection<T>),所以它“确实是”只读的。
  • 它为一些非常好的扩展方法扫清了道路。到目前为止,Tao.NET库只有两个(我知道,很弱),但还有更多。而且,您也可以轻松地制作自己的文件-只需从ArrayBase<T>(也在库中)派生并覆盖this[int]Count属性即可完成。

  • 如果这对您来说很有希望,请随时使用check it out,让我知道您的想法。

    对于您担心这种“语法噪声”的地方,我还是不太清楚100%:在您的代码中还是在调用代码中?

    如果您在自己的封装代码中可以容忍某些“噪音”,那么我建议您包装一个T[]数组并暴露一个碰巧是IList<T>ReadOnlyCollection<T>:
    class ThingsCollection
    {
        ReadOnlyCollection<Thing> _things;
    
        public ThingsCollection()
        {
            Thing[] things = CreateThings();
            _things = Array.AsReadOnly(things);
        }
    
        public IList<Thing> Things
        {
            get { return _things; }
        }
    
        protected virtual Thing[] CreateThings()
        {
            // Whatever you want, obviously.
            return new Thing[0];
        }
    }
    

    是的,您的一端会有些杂音,但这还不错。而且您公开的界面非常干净。

    另一个选择是创建自己的接口(interface)something like IArray<T> ,该接口(interface)包装T[]并提供仅获取索引器。然后揭露那个。这基本上和公开T[]一样干净,但是不会错误地传达可以通过索引设置项目的想法。

    关于c# - 最佳实践列表/数组/ReadOnlyCollection的创建(和用法),我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/4614749/

    10-12 14:55