简体   繁体   English

划分清单 <string> 分成大小相等的子列表N

[英]Divide List<string> into sublists of equal size N

I'm trying to slice a List of strings (size N) and return a range based on the list being sliced into equal parts (X). 我正在尝试对字符串列表(大小为N)进行切片,并基于被切片成相等部分(X)的列表返回范围。

So for instance, if I have a list of say 10 elements, and my number of tiers is 5. 例如,如果我有一个由10个元素组成的列表,而我的层数为5。

Elements 0 and 1 are tier 1. Elements 2 and 3 are tier 2. At the end of the method I return the tier specified in the params. 元素0和1是第1层。元素2和3是第2层。在方法的最后,我返回在params中指定的层。

What I'm struggling with is if the list count isn't divisible by the number of tiers. 我正在努力的是,如果列表计数不能被层数整除。 For instance, 23 / 5 = 4.6. 例如,23/5 = 4.6。 So that means they'll be 5 sets of 4, and then 3 left over. 因此,这将是5组4组,然后剩下3组。 I'd like the result to be 5 tiers of 5, 5, 5, 5, 3 (with the final tier just the remaining number of elements). 我希望结果为5层,5层,5层,5层,5层,3层(最后一层只是剩余的元素数)。

I've included my code so far, but I'm really stuck on how to ensure the list sizes are as equal as possible and how to handle remainders. 到目前为止,我已经包含了我的代码,但是我真的在如何确保列表大小尽可能相等以及如何处理余数方面陷入困境。

// Gets a list and returns a range by the tier specified
public List<string> GetRangeByTierIndex(List<string> listToDivide, int numOfTiers, int tierIndexToGet)
{
    int numOfElementsPerList = listToDivide.Count / numOfTiers;

    int index = (tierToGet - 1) * numOfElementsPerList;

    return listToDivide.GetRange(index, numOfElementsPerList);
}

Note: Forgot to mention, I can't use LINQ for this either (AOT and iOS problems). 注意:忘了提及,我也不能使用LINQ(AOT和iOS问题)。

The idea is to use modulo which is remainder of division of listToDivide.Count by numOfTiers . 这个想法是使用模,这是listToDivide.Count除以numOfTiers余数。 If that remainder is greater than zero all tiers which index is less or equal to that remainder will have one more element. 如果该余数大于零,则索引小于或等于该余数的所有层将具有一个以上的元素。 Because of that, start index of every tier must be corrected also. 因此,还必须更正每个层的起始索引。 Note that I haven't wrote any checks (like if number of elements in main list is zero, numOfTiers < tierIndexToGet , etc... but you can add those checks if you need). 请注意,我还没有编写任何检查(例如主列表中的元素数是否为零, numOfTiers < tierIndexToGet等),但是您可以根据需要添加这些检查)。 Also, this will, for your example, give lists with 5, 5, 5, 4, 4 elements instead of 5, 5, 5, 5, 3 but I think this is even better. 同样,对于您的示例,这将给出包含5、5、5、4、4 5, 5, 5, 4, 4元素的列表,而不是5、5、5、5、3 5, 5, 5, 4, 4元素5, 5, 5, 5, 3但我认为这更好。 Anyway I hope it will be good for your needs. 无论如何,我希望它能满足您的需求。 Code should look something like: 代码应类似于:

public List<string> GetRangeByTierIndex(List<string> listToDivide, int numOfTiers, int tierIndexToGet)
{
    int remaining = listToDivide.Count % numOfTiers;
    int numOfElementsPerList = listToDivide.Count / numOfTiers;
    int index = (tierIndexToGet - 1) * numOfElementsPerList;
    if (remaining > 0)
    {
        // most increase position of index because of numOfElementsPerList correction bellow
        index += tierIndexToGet > remaining ? remaining : tierIndexToGet - 1;
        // first 'remaining-th' tiers will have +1 element
        numOfElementsPerList += tierIndexToGet <= remaining ? 1 : 0;
    }
    return listToDivide.GetRange(index, numOfElementsPerList);
}

Example: 23 and 5. 示例:23和5。

  • 23/5 = 4 // 4 tiers of 5 - use integer division 23/5 = 4 // 4层5-使用整数除法
  • 23%5 = 3 // 1 tier of 3 23%5 = 3 // 1层3

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM