将一个向量拆分为几乎相等的子向量,然后存储到另一个向量中

splitting one vector into almost-equal sub vectors then storing into another vector

我正在尝试将给定的一个大用户向量拆分为 x 个子向量。一切“似乎”都在正常工作,但结果却不对。

std::vector<std::vector<std::string>> split_to_sub_vectors(std::vector<std::string> initial_vector, int thread_amount) {

    std::cout << "initial size: " << initial_vector.size() << std::endl;

    int size_for_splitting = initial_vector.size();


    std::cout << "split amount: " << thread_amount << std::endl;

    int r = size_for_splitting / thread_amount;
    std::cout << r << " need to be in each sub-vector" << std::endl;

    std::cout << "There will be: " << size_for_splitting % thread_amount << " element remaining" << std::endl;

    std::vector<std::vector<std::string>> perm_vector;



    for (int x = 0; x < thread_amount; x++) {

        std::vector<std::string> temp_vector;

        for (int a = 0; a < r; a++) {
            
            hm++;
            std::cout << hm << std::endl;
            temp_vector.push_back(initial_vector[hm]);
        }

        perm_vector.push_back(temp_vector);



    }
 
    std::cout << "Size of vector holding the sub vectors after splitting: " << perm_vector.size() << std::endl;
   
    std::cout << perm_vector[0][0];
    return perm_vector;

运行 此代码将为您提供:

initial size: 7
split amount: 3
2 need to be in each sub-vector
There will be: 1 element remaining
1
2
3
4
5
6
Size of vector holding the sub vectors after splitting: 3
2

我传入的向量称为 test holds strings,就像这样:

    test.push_back("1");
    test.push_back("2");
    test.push_back("3");
    test.push_back("4");
    test.push_back("5");
    test.push_back("6");
    test.push_back("7");

直到最后一个 print 语句之前的所有内容似乎都有效。所以 perm_vector 应该包含 3 个子向量,其中包含主用户给定向量中的每个元素。当您打印 perm_vector[0][0] 时,您希望输出为“1”,但它是 2,而且 7 不应该在向量中,而 6 应该是最后一个,但是因为它开始于2、7在里面。计数器是在函数外部定义的,它从 0 开始。我的问题是为什么它从 2 开始?

即使 hm 从 0 开始,您也可以在使用它之前递增它。可能如果您在内部 for 循环的末尾递增,您可能会得到您期望的输出。很难说出问题,因为我不知道'initial_vector'里有什么,我假设initial_vector[0] = 1?

我发现你的代码有两个问题:

  1. hm 在使用前递增。此外,将其设为全球性没有意义。
  2. size_for_splitting是整数除法的结果,所以少了余数

我修改了您的代码,因此 hm 的问题已解决。我得到了预期的输出 <<1, 2>, <3, 4>, <5, 6>>,如上所述缺少 7

#include <iostream>
#include<vector>
#include<string>

std::vector<std::vector<std::string> > split_to_sub_vectors(std::vector<std::string> initial_vector, int thread_amount) {
    std::cout << "initial size: " << initial_vector.size() << std::endl;
    int size_for_splitting = initial_vector.size();
    std::cout << "split amount: " << thread_amount << std::endl;

    int r = size_for_splitting / thread_amount;
    std::cout << r << " need to be in each sub-vector" << std::endl;
    std::cout << "There will be: " << size_for_splitting % thread_amount << " element remaining" << std::endl;

    std::vector<std::vector<std::string> > perm_vector;

    int hm = 0;
    for (int x = 0; x < thread_amount; x++) {
        std::vector<std::string> temp_vector;
        for (int a = 0; a < r; a++) {
            std::cout << hm << std::endl;
            temp_vector.push_back(initial_vector[hm]);
            hm++;
        }
        perm_vector.push_back(temp_vector);
    }

    std::cout << "Size of vector holding the sub vectors after splitting: " << perm_vector.size() << std::endl;
    return perm_vector;
}

int main()
{
    std::vector<std::string> test;
    test.push_back("1");
    test.push_back("2");
    test.push_back("3");
    test.push_back("4");
    test.push_back("5");
    test.push_back("6");
    test.push_back("7");
    std::vector<std::vector<std::string> > out = split_to_sub_vectors(test, 3);
}

如果你使用 range-v3 库,实现这个逻辑会变得更容易,也更不容易出错:

#include <range/v3/all.hpp>

namespace rs = ranges;
namespace rv = ranges::views;

auto split_to_sub_vectors(std::vector<std::string> initial_vector, int thread_amount) {
    
    auto res = initial_vector 
             | rv::chunk(thread_amount) 
             | rs::to<std::vector<std::vector<std::string>>>;
     
    if (res.back().size() != thread_amount)
         res.pop_back();
  
    return res;
}

这是一个demo