Разделение списка c # - PullRequest
0 голосов
/ 06 июля 2019

Привет, я немного застрял в C #.Я новичок в этом.Это моя проблема:

У меня есть список из 63 двойных чисел (назовем его «большой список»).

Я хочу разбить этот список на 6 списков со следующим правилом:

Первый список состоит из первых 8 элементов большого списка;Второй список переходит от 9-го элемента большого списка к (9 + 8 = 17-й) элемент большого списка;Третий список переходит от 18-го элемента большого списка к (18 + 8 + 1 = 27-й) элемент большого списка;Четвертый список переходит от 28-го элемента большого списка к (28 + 8 + 2 = 38-й) элемент большого списка;Пятый список переходит от 39-го элемента большого списка к (39 + 8 + 3 = 50-й) элемент большого списка;Шестой список переходит от 51-го элемента большого списка к (51 + 8 + 4 = 63-й) элемент большого списка;

Как я могу это сделать?заранее большое спасибо за вашу помощь!

я пробовал таким образом, но это дает мне ошибку "невозможно применить индексирование с помощью [] к выражению группы методов типа"

List listsplitted= новый список ();

        for (int i = 0; i < 6; i++)
        {
            for (int j = 8; j < 8 + i + 1; j++)
            {
                Listsplitted[i] = biglist.Take[j];
            }
        }

Ответы [ 4 ]

2 голосов
/ 06 июля 2019

Вы можете сделать это, используя функцию GetRange :

List<double> part1= big_list.GetRange(0, 8);//Retrieves 8 items starting with index '0'
List<double> part2= big_list.GetRange(8, 9);//Retrieves 9 items starting with index '8'

Или, если вы не хотите давать разные имена для всех частей, вы можете создать список списков:

List<List<double>> listoflists = new List<List<double>>();
listoflists.Add(big_list.GetRange(0, 8));//Retrieves 8 items starting with index '0'
listoflists.Add(big_list.GetRange(8, 9));//Retrieves 9 items starting with index '8'            
for(int i=0; i<listoflists.Count;i++){
    for(int j=0; j<listoflists[i].Count; j++){
        Console.Write(listoflists[i][j] + "  ");
    }
    Console.WriteLine();
}
1 голос
/ 06 июля 2019

Это очень простой подход с расширениями IEnumerable Пропустить и взять

List<double> first = bigList.Take(8).ToList();
List<double> second = bigList.Skip(8).Take(8).ToList();
List<double> third = bigList.Skip(16).Take(9).ToList();
List<double> fourth = bigList.Skip(25).Take(10).ToList();
List<double> fifth = bigList.Skip(35).Take(11).ToList();

// The last one is without Take to get every remaining element
List<double> sixth = bigList.Skip(46).ToList();

Конечно, вы должны проверить, соответствуют ли индексы вашим требованиям. Эти индексы не пропускают никаких элементов из вашего bigList

Вы можете сделать этот подход более общим с чем-то вроде этого

void Main()
{
    var bigList = GetYourBigList();

    List<Tuple<int, int>> positions = new List<Tuple<int, int>>
    {
        new Tuple<int, int>(0,8),
        new Tuple<int, int>(8,8),
        new Tuple<int, int>(16,9),
        new Tuple<int, int>(25,10),
        new Tuple<int, int>(35,11),
        new Tuple<int, int>(46,13)
    };

    List<List<int>> result = SplitTheList(bigList, positions);

    foreach (var list in result)
    {
        foreach (var temp in list)
            Console.WriteLine(temp);
        Console.WriteLine("--------------------");
    }
 }

 List<List<int>> SplitTheList(List<int> r, List<Tuple<int, int>> positions)
 {
    List<List<int>> result = new List<List<int>>();
    foreach(var x in positions)
       result.Add(r.Skip(x.Item1).Take(x.Item2).ToList());
    return result;

 }
0 голосов
/ 06 июля 2019

Если вы можете заменить список массивом, вы можете обойтись без копирования данных. Вы можете использовать ArraySegment (или Span / Memory в более новых версиях языка), чтобы сделать это.

var array = Enumerable.Range(0, 63).Select(i => (double)i).ToArray();

var splitted = new List<ArraySegment<double>>();

int offset = 0;
int count = 8;
for (int i = 0; i < 6; i++)
{
    splitted.Add(new ArraySegment<double>(array, offset, count));
    offset += count;
    count++;
}

// see what we have
foreach (var seg in splitted)
    Console.WriteLine(seg.Offset + " " + seg.Count);

// work with segments
var segment = splitted[3];
segment[5] = 555555;

// the main array has also changed
Console.WriteLine(string.Join(" ", array));

Обратите внимание, что сегменты не хранят копии данных, а ссылаются на данные в основном массиве.

0 голосов
/ 06 июля 2019

если вы настаиваете на том, чтобы выполнить операцию в одном операторе for, вы можете использовать следующий код

const int arrSize = 6;
var splitedLists = new List<List<int>>(arrSize);

var defaultTake = 8;
var defaultSkip = 0;

for (var i = 1; i <= arrSize; i++)
{
    if (i >= 3)
        defaultSkip--;

    splitedLists.Add(array.Skip(defaultSkip).Take(defaultTake + 1).ToList());

    if (i >= 2)
        defaultTake++;

    defaultSkip = defaultSkip + defaultTake + 1;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...