c#将多个数组复制/合并到一个数组中的更好方法

时间:2017-11-16 03:55:34

标签: c# arrays

是否有人能够建议是否有更好的方法将多个阵列复制到一个阵列中?生成的数组必须具有相同顺序的元素,例如for (f in files) { 值,然后是arrayOne值,等等。

以下是我正在执行的按预期工作的模型。寻找一种更聪明的方法。

arraySecond

正如您在arrayN中看到的那样,代码可以变得更长。我有一个最多5个阵列,我试图复制到一个阵列,因此,它是可管理的。我正在使用此技术作为WebAPI的一部分,其中根据要传递给多个Oracle存储过程的业务规则合并oracle参数对象的集合。任何建议在这里表示赞赏。提前致谢。 结果

// Initialise the first array.
string[] arrayOne = new string[5];
arrayOne[0] = "arrayOneValue[0]";
arrayOne[1] = "arrayOneValue[1]";
arrayOne[2] = "arrayOneValue[2]";
arrayOne[3] = "arrayOneValue[3]";
arrayOne[4] = "arrayOneValue[4]";

// Initialise the second array.
string[] arrayTwo = new string[6];
arrayTwo[0] = "arrayTwoValue[0]";
arrayTwo[1] = "arrayTwoValue[1]";
arrayTwo[2] = "arrayTwoValue[2]";
arrayTwo[3] = "arrayTwoValue[3]";
arrayTwo[4] = "arrayTwoValue[4]";
arrayTwo[5] = "arrayTwoValue[5]";

// Initialise the third array.
string[] arrayThree = new string[3];
arrayThree[0] = "arrayThreeValue[0]";
arrayThree[1] = "arrayThreeValue[1]";
arrayThree[2] = "arrayThreeValue[2]";

// string[] arrayN = new string[n]
//.
//.
//.

// Initialise the target array.
string[] finalArray = new string[arrayOne.Length + arrayTwo.Length + arrayThree.Length];
// ArrayN - string[] finalArray = new string[arrayOne.Length + arrayTwo.Length + arrayThree.Length + arrayN.Length];

// Copy/merge the three arrays into the target array.
Array.Copy(arrayOne, 0, finalArray, 0, arrayOne.Length);
Array.Copy(arrayTwo, 0, finalArray, arrayOne.Length, arrayTwo.Length);
Array.Copy(arrayThree, 0, finalArray, (arrayOne.Length + arrayTwo.Length), arrayThree.Length);
//.
//.
//.
//.
// ArrayN - Array.Copy(arrayN, 0, finalArray, (arrayOne.Length + arrayTwo.Length + arrayN), arrayN.Length) ?;

4 个答案:

答案 0 :(得分:3)

您可以使用LINQ .Concat ,这样您就不需要手动处理数组长度和偏移量:

var finalArray = arrayOne.Concat(arrayTwo).Concat(arrayThree).ToArray();

与使用Array.Copy相比,它的性能可能稍差,但这段代码更具可读性,可维护性和错误安全性,这一点更为重要。

答案 1 :(得分:2)

您可以将输入数组放在一个集合中并迭代它们。我只提到这一点,因为这可能比使用LINQ更有效。这取决于您正在处理的数据,但可能不足以产生影响。

在下面的代码中,在我的机器上,LINQ需要9000-13000个刻度(一个刻度= 100 ns),而调用Array.Copy则是~500个刻度。

public static void Benchmark1()
{
    var arr1 = Enumerable.Range(1,10000).ToArray();
    var arr2 = Enumerable.Range(10001,20000).ToArray();
    var arr3 = Enumerable.Range(20001,30000).ToArray();
    var arr4 = Enumerable.Range(30001,40000).ToArray();

    var sw = Stopwatch.StartNew();
    var result = arr1.Concat(arr2).Concat(arr3).Concat(arr4).ToArray();
    sw.Stop();
    Console.WriteLine($"Elpased ticks: {sw.ElapsedTicks}");
}

public static void Benchmark2()
{
    var arr1 = Enumerable.Range(1,10000).ToArray();
    var arr2 = Enumerable.Range(10001,20000).ToArray();
    var arr3 = Enumerable.Range(20001,30000).ToArray();
    var arr4 = Enumerable.Range(30001,40000).ToArray();

    var arrays = new List<int[]>() {arr1, arr2, arr3, arr4};

    var sw = Stopwatch.StartNew();

    int finalLen = 0;
    foreach (var arr in arrays)
    {
        finalLen += arr.Length;
    }

    var result = new int[finalLen];
    int currentPosition = 0;

    foreach (var arr in arrays)
    {
        Array.Copy(arr, 0, result, currentPosition, arr.Length);
        currentPosition += arr.Length;
    }

    sw.Stop();
    Console.WriteLine($"Elpased ticks: {sw.ElapsedTicks}");
}

答案 2 :(得分:1)

通过预先创建一个大数组,然后使用Array.Copy,即使使用大量数组,我们也可以实现非常合理的连接速度:

public static T[] ConcatArrays<T>(params T[][] p)
{
    var position = 0;
    var outputArray = new T[p.Sum(a => a.Length)];
    foreach (var curr in p)
    {
        Array.Copy(curr, 0, outputArray, position, curr.Length);
        position += curr.Length;
    }
    return outputArray;
}

所以,现在我们可以:

string bigArray = ConcatArrays(arrayOne, arrayTwo, arrayThree)

string[][] arrays = new[]{arrayOne, arrayTwo, arrayThree};
string bigArray = ConcatArrays(arrays);

答案 3 :(得分:0)

你必须使用数组吗?使用列表和AddRange()。如果你最终需要一个数组,那么最后只需要调用ToArray()。