如何将数组分成n部分?

问题描述 投票:0回答:8

我有一个字节列表,我想将此列表分成更小的部分。

var array = new List<byte> {10, 20, 30, 40, 50, 60};

此列表有 6 个单元格。例如,我想将其分成 3 部分,每部分包含 2 个字节。

我尝试编写一些for循环并使用二维数组来实现我的目的,但我不知道这是一个正确的方法。

byte[,] array2D = new byte[window, lst.Count / window];
var current = 0;
for (int i = 0; i < rows; i++)
{
    for (int j = 0; j < cols; j++)
    {
        array2D[i, j] = lst[current++];
    }
}
c# arrays multidimensional-array split
8个回答
82
投票

一个好的方法是创建一个通用/扩展方法来分割任何数组。这是我的:

/// <summary>
/// Splits an array into several smaller arrays.
/// </summary>
/// <typeparam name="T">The type of the array.</typeparam>
/// <param name="array">The array to split.</param>
/// <param name="size">The size of the smaller arrays.</param>
/// <returns>An array containing smaller arrays.</returns>
public static IEnumerable<IEnumerable<T>> Split<T>(this T[] array, int size)
{
    for (var i = 0; i < (float)array.Length / size; i++)
    {
        yield return array.Skip(i * size).Take(size);
    }
}

而且,这个解决方案被推迟了。然后,只需在阵列上调用

Split(size)
即可。

var array = new byte[] {10, 20, 30, 40, 50, 60};
var splitArray = array.Split(2);

根据要求,这是从数组获取方形二维数组的通用/扩展方法:

/// <summary>
/// Splits a given array into a two dimensional arrays of a given size.
/// The given size must be a divisor of the initial array, otherwise the returned value is <c>null</c>,
/// because not all the values will fit into the resulting array.
/// </summary>
/// <param name="array">The array to split.</param>
/// <param name="size">The size to split the array into. The size must be a divisor of the length of the array.</param>
/// <returns>
/// A two dimensional array if the size is a divisor of the length of the initial array, otherwise <c>null</c>.
/// </returns>
public static T[,]? ToSquare2D<T>(this T[] array, int size)
{
    if (array.Length % size != 0) return null;

    var firstDimensionLength = array.Length / size;
    var buffer = new T[firstDimensionLength, size];

    for (var i = 0; i < firstDimensionLength; i++)
    {
        for (var j = 0; j < size; j++)
        {
            buffer[i, j] = array[i * size + j];
        }
    }

    return buffer;
}

玩得开心!


16
投票

使用Linq

public List<List<byte>> SplitToSublists(List<byte> source)
{
    return source
             .Select((x, i) => new { Index = i, Value = x })
             .GroupBy(x => x.Index / 100)
             .Select(x => x.Select(v => v.Value).ToList())
             .ToList();
}

简单使用即可

var sublists = SplitToSublists(lst);

7
投票

这里有列表列表

array.Select((s,i) => array.Skip(i * 2).Take(2)).Where(a => a.Any())

或者这个有项目列表

array.SelectMany((s,i) => array.Skip(i * 2).Take(2)).Where(a => a.Any())


0
投票
Public Shared Function splitArrayIntoSmallerArrays(Of someObject)(arrayOfSomeObject As someObject(), chunkSize As Integer) As List(Of someObject())

    Dim output = New List(Of someObject())
    Dim newestArray = New List(Of someObject)
    For i = 0 To arrayOfSomeObject.Count - 1

        newestArray.Add(arrayOfSomeObject(i))
        If newestArray.Count = chunkSize Then
            output.Add(newestArray.ToArray)
            newestArray = New List(Of someObject)
        End If
    Next
    output.Add(newestArray.ToArray)
    Return output
End Function

0
投票

你可以做一个扩展方法:

public static class IEnumerableExtensions
{
    public static IEnumerable<T[]> Split<T>(this IEnumerable<T> self, int chunkSize)
    {
        using var enu = self.GetEnumerator();
        var buffer = new List<T>();
        while(enu.MoveNext())
        {
            var v = enu.Current;
            buffer.Add(v);
            if (buffer.Count != chunkSize) continue;
            yield return buffer.ToArray();
            buffer = new List<T>();
        }
        if (buffer.Count == 0) yield break;
        yield return buffer.ToArray();
    }
}

并像这样使用它:

var test = Enumerable.Range(0, 200);
var split = test.Split(7).ToArray();

-1
投票

您可能想尝试一下。

var bytes = new List<byte>(10000);
int size = 100;
var lists = new List<List<byte>>(size);
for (int i = 0; i < bytes.Count; i += size)
{
        var list = new List<byte>();
        list.AddRange(bytes.GetRange(i, size));
        lists.Add(list);
}

-1
投票

如果您有一个要划分的数组,但通过这个简单的解决方案,除法具有其余部分,您可以将缺少的元素平等地共享到各个“块”中:

    public static List<int[]> SplitArrey(int[] arrInput, int nColumn) {

    List<int[]> result = new List<int[]>(nColumn);

    int itemsForColum = arrInput.Length / nColumn;  
    int countSpareElement = arrInput.Length - (itemsForColum * nColumn);    

    // Add and extra space for the spare element
    int[] newColumLenght = new int[nColumn];
    for (int i = 0; i < nColumn; i++)
    {
        int addOne = (i < countSpareElement) ? 1 : 0;
        newColumLenght[i] = itemsForColum + addOne;
        result.Add(new int[itemsForColum + addOne]);
    }

    // Copy the values
    int offset = 0;
    for (int i = 0; i < nColumn; i++)
    {
        int count_items_to_copy = newColumLenght[i];
        Array.Copy(arrInput, offset, result[i], 0, count_items_to_copy);
        offset += newColumLenght[i];
    }
    return result;
}

然后:

int[] arrInput = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12 };
var result = SplitArrey(arrInput, 5);
foreach (var item in result) {
 Console.WriteLine("   {0}", String.Join(" ", item));
}

结果是:

1 2 3 
4 5 6 
7 8 
9 10 
11 12
© www.soinside.com 2019 - 2024. All rights reserved.