Отображение вектора в определенный диапазон - PullRequest
0 голосов
/ 23 декабря 2018

У меня стандартный вектор содержит, например, следующие элементы

[-6, -7, 1, 2]

Мне нужно отобразить эти элементы в диапазоне от 1 до 4. т.е. мне нужен векторчтобы быть похожим на это

[2, 1, 3, 4]

Обратите внимание, что: наименьшее значение в первом векторе (-7) было сопоставлено с наименьшим значением во втором векторе (1).Как я могу добиться этого с STL?

Ответы [ 3 ]

0 голосов
/ 23 декабря 2018

Использование вспомогательного вектора пар:

std::vector<int> a { -6, -7, 1, 2 };

std::vector<std::pair<int, int>> tmp;
for (int i = 0; i < (int) a.size(); ++i) {
    tmp.push_back({ a[i], i });
}

std::sort(tmp.begin(), tmp.end());

std::vector<int> b;
for (auto & x : tmp) {
    b.push_back(x.second + 1);
}

Демонстрация


Использование вспомогательного приоритета-пары пар (чтобы избежать явной сортировки):

std::vector<int> a { -6, -7, 1, 2 };

std::priority_queue<std::pair<int, int>> tmp;
for (std::size_t i = 0; i < a.size(); ++i) {
    tmp.push({ -a[i], i});
}

std::vector<int> b;
do {
    b.push_back(tmp.top().second + 1);
} while (tmp.pop(), !tmp.empty());

Демо

0 голосов
/ 24 декабря 2018

Имея только стандартную библиотеку, существующую в C ++ 17 (или, на самом деле, C ++ 11), вы создаете вектор индексов и сортируете его, используя себя в качестве проекции:

vector<int> idxs(values.size());
iota(idxs.begin(), idxs.end(), 1);
sort(idxs.begin(), idxs.end(), [&](int i, int j){
    return values[i-1] < values[j-1];
});

Другой способ генерации индексов - использовать generate_n:

vector<int> idxs;
generate_n(back_inserter(idxs),
    values.size(),
    [cnt=1]() mutable { return cnt++; });
// same sort()
0 голосов
/ 23 декабря 2018

С range-v3 :

std::vector<int> v{-6, -7, 1, 2};
auto res = ranges::view::ints(1, 1 + (int)v.size()) | ranges::to_vector;

ranges::sort(ranges::view::zip(v, res));

Демо

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...