Пожалуйста, объясните этот код, который использует std:: ignore
Я читаю документацию на std::ignore
из cppreference. Мне трудно понять истинную цель этого объекта, и примерный код не оправдывает этого. Например, в приведенном ниже коде, как и почему inserted
установлено значение true? Мне это не имеет смысла.
#include <iostream>
#include <string>
#include <set>
#include <tuple>
int main()
{
std::set<std::string> set_of_str;
bool inserted;
std::tie(std::ignore, inserted) = set_of_str.insert("Test");
if (inserted) {
std::cout << "Value was inserted sucessfully\n";
}
}
Если кто-то может объяснить мне код, это будет оценено. Спасибо.
Ответы
Ответ 1
set::insert
возвращает пару, где сначала находится итератор, к вставленному элементу, а второй - к bool, указав, был ли вставлен элемент.
std::tie
создает кортеж ссылок lvalue. При присвоении результата из insert
он позволяет вам установить переменные в tie
в результаты вставки в членах return pair
first
и second
.
std::ignore
- это значение, которое может быть присвоено без эффекта.
В принципе, этот код игнорирует итератор для элемента, в который был вставлен "Test"
, и присваивает inserted
члену second
пары, возвращаемой set::insert
, которая указывает, был ли вставлен элемент.
Ответ 2
Я думаю, что ответ Дэйва довольно хорош, но я хотел бы немного объяснить, зачем использовать такой подход.
В других языках, таких как Scala, Haskell или Python, у вас обычно есть кортежи (являющиеся парой кортежей из двух элементов), и у них есть этот идиоматический способ присвоить их переменным:
(var1,...,varN) = func_returning_tuple()
Это имеет целью расширить семантическое значение вашего кода и улучшить его читаемость, в противном случае у вас будет одна переменная без семантики для их элементов (например, t.first и т.д.), а в С++ - доступ к значениям кортежей, которые вы должны использовать:
varN = std::get<N>(my_tuple);
Итак, используя только галстук, вы можете упростить чтение кода примера следующим образом:
std::tie( element_iterator, inserted ) = set_of_str.insert("test");
И затем используйте ваши изолированные переменные по своему усмотрению, что улучшает поведение других (и даже самих себя) следующих операторов вашего кода.
std::ignore
используется, когда вы не заботитесь о том, что возвращается, на некоторых других языках, у которых также есть этот ресурс, в Scala, например, это символ подчеркивания. Например, если я использую функцию insert в карте, и значение уже существует, оно просто возвращает пару, содержащую (iterator,false)
, поэтому, если я хочу, чтобы итератор для некоторого ключа, даже если мне все равно, если он уже существует на карте, Я могу сделать это с помощью этой строки:
std::tie( element_iterator, std::ignore ) = set_of_str.insert("test");
То, как С++ решает эту проблему с читабельностью кортежей и пар.