32

編集:Take / Skipメソッドを試しましたが、次のエラーが発生します:

Cannot implicitly convert type 'System.Collections.Generic.IEnumerable<string>' to   
'string[]'. An explicit conversion exists (are you missing a cast?)

Saeedのコードをコピーしたので、何が間違っているのかわかりません。

文字列配列(20から300のアイテムを含む)があり、最初の配列の中央から2つの別々の配列に分割したいと思います。

forループを使用してこれを行う方法は知っていますが、より高速でより良い方法があるかどうかを知りたいと思います。また、アイテムの数が奇数であっても、配列を正しく分割できる必要があります。例:

string[] words = {"apple", "orange", "banana", "pear", "lemon"};
string[] firstarray, secondarray;
SplitArray(words, out firstarray, out secondarray); // Or some other function
// firstarray has the first 3 of the items from words, 'apple', 'orange' and 'banana'
// secondarray has the other 2, 'pear' and 'lemon'
4

7 に答える 7

70

linqを使用できます:

firstArray = array.Take(array.Length / 2).ToArray();
secondArray = array.Skip(array.Length / 2).ToArray();

元の配列サイズのパリティにもかかわらず、なぜこれが機能するのですか?

firstArrayはarray.Length / 2要素を受け取り、2番目の配列は最初の要素をスキップしarray.Length / 2ます。これは、これら2つの配列の間に競合がないことを意味します。もちろん、要素の数が奇数の場合、配列を2つの等しいサイズの部分に分割することはできません。

前半(奇妙な場合)にもっと多くの要素が必要な場合は、次のようにします。

firstArray = array.Take((array.Length + 1) / 2).ToArray();
secondArray = array.Skip((array.Length + 1) / 2).ToArray();
于 2012-05-22T10:53:33.307 に答える
8
string[] words = {"apple", "orange", "banana", "pear", "lemon"};
int mid = words.Length/2;
string[] first = words.Take(mid).ToArray();
string[] second = words.Skip(mid).ToArray();
于 2012-05-22T10:53:41.983 に答える
7

LINQを使用したくない/使用できない場合は、次のようにすることができます。

    string[] words = { "apple", "orange", "banana", "pear", "lemon" };
    string[] firstarray, secondarray;
    int mid = words.Length / 2;
    firstarray = new string[mid];
    secondarray = new string[words.Length - mid];
    Array.Copy(words, 0, firstarray, 0, mid);
    Array.Copy(words, mid, secondarray, 0, secondarray.Length);
于 2012-05-22T11:00:34.450 に答える
4

指定した数の部分に分割する、より一般化されたアプローチ:

public static IEnumerable<IEnumerable<T>> Split<T>(this IEnumerable<T> list, int parts)
        {
          return list.Select((item, index) => new {index, item})
                       .GroupBy(x => (x.index + 1) / (list.Count()/parts) + 1)
                       .Select(x => x.Select(y => y.item));
        }

*編集されたありがとうskarmats

于 2012-05-22T10:57:43.430 に答える
3
string[] words = { "apple", "orange", "banana", "pear", "lemon" };
var halfWay = words.Length/2;

var firstHalf = words.Take(halfWay);
var secondHalf = words.Skip(halfWay);
于 2012-05-22T10:56:47.890 に答える
2

範囲表記を使用すると、これを非常に簡単に実現できます。

var x = new[] {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11};
var pivot = x.Length / 2;
var p1 = x[..pivot];
var p2 = x[pivot..];
于 2021-02-03T21:55:58.327 に答える
-2

誰かが代わりに関数を使用したい場合に備えて:

    static void Main(string[] args)
    {
        string[] ar = { "apple", "orange", "banana", "pear", "lemon" };

        int half =  ar.Length / 2;

        //  Console.WriteLine(string.Join(',', Split(ar,0, half)));

        Console.WriteLine(string.Join(',', Split(ar,half, ar.Length)));

        Console.ReadKey();
    }


    public static IEnumerable<T> Split<T>(IEnumerable<T> items, int start, int end)
    {
        return items.Skip(start).Take(end);
    }
于 2019-08-18T23:38:19.360 に答える