Эта идея может быть реализована с помощью гетерогенного контейнера tuple
, который позволит хранить векторы, содержащие элементы различных типов.
В частности, мы можем определить простую структуру данных следующим образом
template <typename ...Ts>
using vector_tuple = std::tuple<std::vector<Ts>...>;
В начальном случае из представленного примера три вектора a_values
, b_values
, c_values
просто соответствуют типу vector_tuple<int, float, std::string>
.Добавление дополнительного вектора просто требует добавления дополнительного типа в нашу коллекцию.
Индексация в нашей новой коллекции также проста, учитывая коллекцию
vector_tuple<int, float, std::string> my_vec_tup;
, у нас есть следующие методы для извлечения a_values:b_values и c_values
auto const &a_values = std::get<0>(my_vec_tup);
auto const &b_values = std::get<1>(my_vec_tup);
auto const &c_values = std::get<2>(my_vec_tup);
Обратите внимание, что контейнер tuple
индексируется во время компиляции, что отлично, если вы знаете предполагаемый размер во время компиляции, но в противном случае будет неподходящим.
В приведенном описании проблемы число векторов, по-видимому, решается во время компиляции, а соглашение об именовании кажется произвольным и постоянным (т. Е. Индекс выигранных векторов 'должны быть изменены во время выполнения).Следовательно, кортеж векторов представляется подходящим решением, если вы связываете каждое имя с целочисленным индексом.
Что касается второй части вопроса (т. Е. Итерации по каждому вектору), если выс помощью C ++ 17 хорошая новость заключается в том, что вы можете просто использовать функцию std::apply
, чтобы сделать это: https://en.cppreference.com/w/cpp/utility/apply Все, что требуется, - это передать функцию, которая принимает вектор (вы можете определить соответствующиеперегрузка для обработки каждого контейнера отдельно), и ваш кортеж к std::apply
.
Однако для более ранних версий C ++ вам нужно будет реализовать собственную функцию for_each.К счастью, эта проблема уже решена: Как перебрать элементы std :: tuple?