【问题标题】:Row-wise concatenate a list of jagged arrays in c#在c#中逐行连接锯齿状数组的列表
【发布时间】:2019-03-18 17:18:57
【问题描述】:

我希望帮助*创建一种方法或 (linq) 表达式,该方法或 (linq) 表达式可以按行连接锯齿状数组的列表(不同长度),如下所示:

List<double[][]> orgArrayList = new List<double[][]>();

double[][] one = {
new [] {5d, 6},
new [] {7d, 9}};

double [][] two =  {
new [] {5d, 6},
new [] {7d, 9}};

double [][] three= {
new [] {5d, 6},
new [] {7d, 9}};

orgArrayList.AddRange(new[] {one, two, three});

所以结果数组将等于这个:

double[][] expected = {
new [] {5d, 6, 5, 6, 5, 6},
new [] {7d, 9, 7, 9, 7, 9}};

我的输入列表中的锯齿状数组的数量将 >=1。单个列表中的所有数组都将具有 2 个维度,但没有一个 2 个维度具有固定/已知长度(大小)。

*'help' 委婉地表示有人告诉我该怎么做

【问题讨论】:

  • 试试这个策略:将数组转换为列表,与 AddRange 合并,再转换回数组。
  • 投反对票的人能不能这么好心,帮助我提高我的“问题发布技能”,谢谢:)

标签: c# arrays concatenation


【解决方案1】:

您可以从这样的开始,将add[] 的每一行的元素附加到src[] 的行,生成一个新的二维数组:

public static double[][] AppendToRows(double[][] src, double[][] add)
{
    // Allocate new array to hold elements from src[] and add[]
    double[][] res = new double[src.Length][];

    // Append elements to each row of res[]
    for (int i = 0;  i < src.Length;  i++)
    {
        // Allocate row res[i] large enough to hold elements from src[i] and add[i]
        res[i] = new double[src[i].Length + add[i].Length];

        // Copy/append elements from src[i] to res[i]
        int ri = 0;
        for (int j = 0;  j < src[i].Length;  j++)
            res[i][ri++] = src[i][j];

        // Copy/append elements from add[i] to res[i]
        if (i >= add.Length)
            continue;
        for (int j = 0;  j < add[i].Length;  j++)
            res[i][ri++] = add[i][j];
    }
    return res;
}

要将多个数组附加在一起,只需多次调用此方法,每个需要连接到结果数组的附加数组一次。

更全面的解决方案是采用List&lt;double[][]&gt; 的输入数组,并在构建结果的每一行时循环遍历列表中的每个数组。但我把它留给读者作为练习。

【讨论】:

  • 干杯@大卫;为两个数组创建一个方法,然后使用该方法循环遍历列表似乎很简单......一旦人们认识到它是一种可能性:)
【解决方案2】:

您可以创建一个扩展,它将按照您需要的方式连接数组,因此它看起来像 Linq:

public static class Extension
{
    public static T[][] ConcatArrays<T>(this T[][] array, T[][] concatWith)
    {

        var max = Math.Max(array.Length, concatWith.Length);
        var result = new T[max][];
        for (var index = 0; index < max; index++)
        {
            var list = new List<T>();
            if (index < array.Length)
            {
                list.AddRange(array[index]);                   
            }

            if (index < concatWith.Length)
            {
                list.AddRange(concatWith[index]);
            }

            result[index] = list.ToArray();
        }

        return result;
    }
}

所以这个的用法是:

var expected = one.ConcatArrays(two).ConcatArrays(three);

希望有意义

【讨论】:

    【解决方案3】:

    作为我用例的最终解决方案,我简单地将 David 和 Valdimir 的答案组合成一个可以处理不同长度 (>=1) 列表的单一方法

    // ========================================
    // My interpretation of David's suggestion
    // using Valdimir's solution as a basis
    // ========================================
    public static double[][] RowWiseConcatListedJaggedArrays(List<double[][]> listOfJaggedArray)
    {
        var resArray = listOfJaggedArray[0];
    
        for (int rInd = 1; rInd < listOfJaggedArray.Count; rInd++)
        {
            resArray = resArray.ConcatArrays(listOfJaggedArray[rInd]);
        }
    
        return resArray;
    }
    

    然后把所有东西放在一起......

    using System;
    using System.Collections.Generic;
    
    namespace RowWiseConcat
    {
        public static class Extension
        {
            // ====================
            // Vladimir's solution
            // ====================
            public static T[][] ConcatArrays<T>(this T[][] array, T[][] concatWith)
            {
    
                var max = Math.Max(array.Length, concatWith.Length);
                var result = new T[max][];
                for (var index = 0; index < max; index++)
                {
                    var list = new List<T>();
                    if (index < array.Length)
                    {
                        list.AddRange(array[index]);
                    }
    
                    if (index < concatWith.Length)
                    {
                        list.AddRange(concatWith[index]);
                    }
    
                    result[index] = list.ToArray();
                }
    
                return result;
            }
        }
    
        class Program
        {
            // ========================================
            // My interpretation of David's suggestion
            // using Valdimir's solution as a basis
            // ========================================
            public static double[][] RowWiseConcatListedJaggedArrays(List<double[][]> listOfJaggedArray)
            {
                var resArray = listOfJaggedArray[0];
    
                for (int rInd = 1; rInd < listOfJaggedArray.Count; rInd++)
                {
                    resArray = resArray.ConcatArrays(listOfJaggedArray[rInd]);
                }
    
                return resArray;
            }
    
            static void Main(string[] args)
            {
    
                // ... do something that results in orgArrayList, e.g.
                double[][] one =
                {
                    new[] {5d, 6},
                    new[] {7d, 9}
                };
                double[][] two =
                {
                    new[] {5d, 6},
                    new[] {7d, 9}
                };
                double[][] three =
                {
                    new[] {5d, 6},
                    new[] {7d, 9}
                };
    
                List<double[][]> orgArrayList = new List<double[][]>()
                    { one, two, three};
    
                // Concat list items
                var resArray = RowWiseConcatListedJaggedArrays(orgArrayList);
    
                // ... continue with resArray
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2023-03-04
      • 1970-01-01
      • 2019-11-17
      • 2011-06-10
      • 2011-10-09
      • 2019-02-18
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多