Как перебрать все элементы в двух векторах?

Есть два вектора. Нужно перебрать все их элементы и сделать одно и то же действие сначала над элементами одного вектора, потом второго.

std::vector<int> mas1 = {0,1,2,3};
std::vector<int> mas2 = {4,5,6,7,8,9};
for (auto num : mas1) { do_smth (); }
for (auto num : mas2) { do_smth (); }

Можно ли сделать то же самое одним циклом, но не создавая общий вектор?


Ответы (2 шт):

Автор решения: user7860670

Чтобы избежать повторения do_smth или содержимого цикла можно итерироваться по view от коллекций (или даже ranges склеить), что не потребует динамического выделения памяти в отличии от создания одного вектора:

auto Make_View(auto & container)
{
    return ::std::span{container.begin(), container.end()};
}
...
std::vector<int> mas1 = {0,1,2,3};
std::vector<int> mas2 = {4,5,6,7,8,9};
for (auto & view: {Make_View(mas1), Make_View(mas2)})
{
    for (auto & num: view)
    {
       do_smth ();
    }
}

или вообще в лоб итерироваться даже без view:

std::vector<int> mas1 = {0,1,2,3};
std::vector<int> mas2 = {4,5,6,7,8,9};
for (auto & p_view: {&mas1, &mas2})
{
    for (auto & num: *p_view)
    {
       do_smth ();
    }
}
→ Ссылка
Автор решения: Chorkov

std::views::join - объединяет массив массивов в один длинный длинный виртуальный массив. Проблема в том, что это не может быть массив ссылок (это запрещено), и не может быть массив собственно массивов (требует копирования), но может быть массив виртуальных массивов - просмотровщиков (views) :

int main() {
    std::vector<int> mas1 = {0,1,2,3};
    std::vector<int> mas2 = {4,5,6,7,8,9};
    for( auto num : std::views::join(
                         std::array{ // array - не требует динамического выделения памяти (размер известен на этапе компиляции)
                                     std::views::all(mas1), 
                                     std::views::all(mas2)  // std::views::all - тоже что Make_View в ответе ниже 
                                   } 
                                   ) 
       )
   {
       std::cout<<num<<std::endl;
   }
}
→ Ссылка