返回数组片段

时间:2008-12-18 23:09:02

标签: c#-3.0 extension-methods

我需要从数组中获取数组片段。我厌倦了使用Array.Copy()。 new ArraySegment(..)。Array返回原始的[full]数组。下面的是我提出的,但我觉得它很蹩脚。有更好的方法吗?

class Program
{
    static void Main(string[] args)
    {
        var arr = new ArraySegment<byte>(new byte[5] { 5, 4, 3, 2, 1 }, 0, 2).ArrayFragment();
        for (int i = 0; i < arr.Length; i++)
            Console.WriteLine(i);
        Console.Read();
    }
}

static class Extensions
{
    public static T[] ArrayFragment<T>(this ArraySegment<T> segment)
    {
        var arr = new T[segment.Count];
        Array.Copy(segment.Array, segment.Offset, arr, 0, segment.Count);
        return arr;
    }
}

class Program { static void Main(string[] args) { var arr = new ArraySegment<byte>(new byte[5] { 5, 4, 3, 2, 1 }, 0, 2).ArrayFragment(); for (int i = 0; i < arr.Length; i++) Console.WriteLine(i); Console.Read(); } } static class Extensions { public static T[] ArrayFragment<T>(this ArraySegment<T> segment) { var arr = new T[segment.Count]; Array.Copy(segment.Array, segment.Offset, arr, 0, segment.Count); return arr; } }

提前致谢。

更新: 以上只是一个例子 我有一个方法:byte [] CalculateXXX(byte [] key,byte [] message); 我在这个方法中做数组操作。我想返回数组的一部分。 ArraySegment没有实现IEnumerable,并且它不返回只包含新的ArraySegment(arr ...)的数组.Alray返回完整的原始数组。

var rval = new byte[4]; //new ArraySegment(finalOutputBuffer, 0, 4).SegmentedArray(); Array.Copy(finalOutputBuffer, 0, rval, 0, 4);

我发现我必须执行上述操作才能返回数组片段。只是想知道是否有更好的方法来返回数组的片段[作为新数组]。

3 个答案:

答案 0 :(得分:1)

Vyas,我真的抱歉发布了这个无用的****堆。自从我实际使用ArraySegment以来已经很久了,我只是假设它实现了(或多或少)一致的界面。有人(乔恩?)请告诉我在实施这个无用的结构时使用了哪些药物。

最后,总而言之,最好的解决方案可能是实现您自己的ArraySegment版本,只做正确的事。

我不明白您使用ArraySegment时遇到的问题。这里没有额外的开销,如果这就是你的意思,因为没有复制原始数据。相反,ArraySegment提供了数据的轻量级视图。

这样做,将您的(返回)类型从T[]更改为IEnumerable<T>,或者,如果您需要索引访问,则更改为IList<T>。通常更喜欢在方法签名中使用接口类型,并完全避免使用数组类型。理由非常简单:它会使您的问题消失,使界面更加灵活,面向未来。它还提供了更好的信息隐藏,因为它隐藏了与此方法的使用者无关的实现部分。

答案 1 :(得分:1)

更好地定义。 ArraySegment的缺点是什么?你有什么问题,它没有解决?


编辑:好的,我现在明白你的观点,但这是错误的。从某种意义上说,它可能是一个错误,你觉得它应该做得更多,但它确实完成了应该做的事情。它允许您将信息传递给一段关于您希望使用的数组的代码,以及要使用的数组部分。

它不提供IEnumerable或任何能够提供数组窄视图的东西,即。 x [0]不会为您提供该段的第一个元素,也不能对其进行预测。

所以是的,它本身相当无用,但是你无法获得 一个数组的内容,而且还是一个更大数组的一部分。

您可以轻松创建自己的类似集合的类,它引用数组并将数组用作存储,并提供索引,枚举等。

但这不是这种结构的作用。我想这里的主要问题是他们通过它的名字让你期待更多。

答案 2 :(得分:0)

C#btw中迭代器设计不佳的另一个副作用。有许多实例类似(就像'跛脚'),它只是简单的好设计能够传递或指向或控制段(也称为概念称为范围)没有所有的archane shickanery ..复制语义与否,数组也是一个定义明确的概念。

只需使用C ++。 : - )