Сегментация 2D вектора в C ++

0

В настоящее время у меня есть 2D-вектор, содержащий 600 значений "блоки" с 2 значениями в каждом блоке. Я хочу сделать, создать новый вектор векторов, который сегментирует блоки, поэтому вместо значений, хранящихся как 2, я буду хранить 10 или любое количество блоков, которые позволят мне.

Вот пример, используя небольшой вектор векторов:

std::vector<std::vector<double> > values = { {1, 2}, {2, 4}, {5, 8}, {4, 5} };

Таким образом, это может быть сегментировано на 2, и поэтому блок будет содержать 4 блока. Например

std::vector<std::vector<double> > values2 = { {1, 2, 2, 4}, {5, 8, 4, 5} }; 

Теперь в векторе векторов есть два блока, и каждый из этих блоков теперь содержит 4 значения.

Но как это будет возможно? Я использую только сегментирование 1D-векторов, поэтому для этой задачи можно было бы использовать std::copy и std::back_inserter для решения этой проблемы? В реальной проблеме у меня есть 600 блоков, содержащих по 2 значения в каждом.

благодаря

  • 0
    Это звучит не очень сложно, вы уже пробовали? Похоже, около 4 строк кода. Еще проще, если сначала выровнять первый вектор, но это не нужно. Лично я не стал бы пытаться использовать std :: copy или std :: back_inserter, просто написал цикл.
  • 0
    @Salgar Но нужна ли мне переменная на месте, скажем 1) iterate through the entire number of vectors 2) check if the value is less 4 3) push that vector to the new 2D vector ? Концепция кажется мне очень размытой
Показать ещё 1 комментарий
Теги:
vector

1 ответ

2
Лучший ответ

Вот код для упрощенного примера. Надеюсь, это поможет или хотя бы покажет правильное направление.

#include <iostream>
#include <vector>
#include <algorithm>

int main() 
{
    typedef std::vector<std::vector<double>>::size_type size_type;
    const size_type N = 4;


    std::vector<std::vector<double>> v1 = { {1, 2}, {2, 4}, {5, 8}, {4, 5}, { 7, 8 } };

    for ( const auto &v : v1 )
    {
        for ( double x : v ) std::cout << x << ' ';
        std::cout << std::endl;
    }

    std::cout << std::endl;

    size_type n = 
        std::accumulate( v1.begin(), v1.end(), size_type( 0 ),
                         [] ( size_type acc, const std::vector<double> &v )
                         {
                            return ( acc + v.size() );
                         } );

    std::vector<std::vector<double>> v2( ( n + N - 1 ) / N );

    std::cout << "v2.size() = " << v2.size() << std::endl;

    auto it = v1.begin();

    for ( std::vector<double> &v : v2 )
    {
        for ( size_type i = 0; i < N / 2 && it != v1.end(); ++it, ++i )
        {
            v.insert( v.end(), ( *it ).begin(), ( *it ).end() );
        }
    }

    for ( const auto &v : v2 )
    {
        for ( double x : v ) std::cout << x << ' ';
        std::cout << std::endl;
    }

    std::cout << std::endl;

    return 0;
}

Выход

1 2 
2 4 
5 8 
4 5 
7 8 

v2.size() = 3
1 2 2 4 
5 8 4 5 
7 8 

Если ваш компилятор не поддерживает C++ 11, то этот диапазон основан на

    auto it = v1.begin();

    for ( std::vector<double> &v : v2 )
    {
        for ( size_type i = 0; i < N / 2 && it != v1.end(); ++it, ++i )
        {
            v.insert( v.end(), ( *it ).begin(), ( *it ).end() );
        }
    }

может быть заменено

    typedef std::vector<std::vector<double>>::iterator iterator;

    iterator it1 = v1.begin();

    for ( iterator it2 = v2.begin(); it2 != v2.end(); ++it2 )
    {
        for ( size_type i = 0; i < N / 2 && it1 != v1.end(); ++it1, ++i )
        {
            ( *it2 ).insert( ( *it2 ).end(), ( *it1 ).begin(), ( *it1 ).end() );
        }
    }

Кстати, это тот случай, когда лучше использовать диапазон, основанный вместо стандартного алгоритма. :)

Например

size_type n = 0;
for ( const auto &v : v1 ) n += v.size();
  • 0
    Эй, спасибо за это. Это имеет смысл, однако я не могу использовать C ++ 11 из-за стандартов, которые я использую. Я постараюсь написать решение из этого, хотя
  • 0
    @ user1326876 Вы можете заменить диапазон на основе обычного цикла for и инициализировать вектор с помощью push_back. Это не в устной форме. Вы можете проверить мой код на www.ideone.com, выбрав язык C ++ 11
Показать ещё 3 комментария

Ещё вопросы

Сообщество Overcoder
Наверх
Меню