Использование std::move на pair.first делает недействительным pair.second?
У меня есть следующий код в моем проекте на данный момент:
std::vector<int> vectorOfFirsts;
std::set<double> setOfSeconds;
std::list<std::pair<int,double>> cachedList;
// do something to fill the list
for (const auto& pair : cachedList)
{
vectorOfFirsts.push_back(pair.first);
setOfSeconds.insert(pair.second);
}
Этот список будет очень большим и необходим только для заполнения вектора и набора (т. Е. Его содержимое может быть признано недействительным). Мой вопрос сейчас, если следующая оптимизация является хорошей идеей:
for (const auto& pair : cachedList)
{
vectorOfFirsts.push_back(std::move(pair.first));
setOfSeconds.insert(std::move(pair.second));
}
Будет ли вызов std::move на pair.first каким-то образом лишать законной силы pair.second? И будет ли этот код обеспечивать ускорение цикла? Я знаю, что, вероятно, было бы неплохо заполнить вектор / набор вместо списка, но список заполняется с помощью какого-то унаследованного кода, над которым у меня нет контроля / нет времени копаться.
2 ответа
Будет ли вызов std::move на pair.first каким-то образом лишать законной силы pair.second?
Нет. first
а также second
совершенно разные переменные, происходящие в некотором объекте класса. Перемещение одного не влияет на другое.
И будет ли этот код обеспечивать ускорение цикла?
Это зависит от типов. Точка move
Что-то значит переводить ресурсы, в основном. Поскольку пары здесь int
с и double
s, ресурсы не задействованы, поэтому передавать нечего. Если бы это была пара некоторого матричного типа и некоторого тензорного типа, каждый с некоторым внутренним динамически распределенным буфером, то это могло бы улучшить производительность.
Стоп.
Найдите минутку, чтобы подумать об этом коде. Встроенные комментарии
// step one - iterate through cachedList, binding the dereferenced
// iterator to a CONST reference
for (const auto& pair : cachedList)
{
// step 2 - use std::move to cast the l-value reference pair to an
// r-value. This will have the type const <pairtype> &&. A const
// r-value reference.
// vector::push_back does not have an overload for const T&& (rightly)
// so const T&& will decay to const T&. You will copy the object.
vectorOfFirsts.push_back(std::move(pair.first));
// ditto
setOfSeconds.insert(std::move(pair.second));
}
Это должно быть:
for (auto& pair : cachedList)
{
vectorOfFirsts.push_back(std::move(pair.first));
setOfSeconds.insert(std::move(pair.second));
}
И да, это тогда становится действительным и законным использованием движения.