TGViewer
Грокаем C++ Грокаем C++ @grokaemcpp · 9.36K subscribers
Post #424 5.12K
​​Присвоение лямбды
#новичкам

Изучение лямбда выражений - не самая простая задача для начинающего плюсовика. Сложные термины, какие-то замыкания, списки захвата и прочее. В общем, непросто. И с виду можно подумать, что 2 одинаковые лямбды можно присваивать друг другу с легкостью. То есть может показаться, что такой код валидный:

int main() {
auto test = [](){};
test = [](){};

return 0;
}


Однако он генерирует примерно следующую ошибку:

In function ‘int main()’:
error: no match for ‘operator=’ in ‘test = <lambda closure object>main()::<lambda()>{}’
note: candidate is:
note: main()::<lambda()>& main()::<lambda()>::operator=(const main()::<lambda()>&) <deleted>
no known conversion for argument 1 from ‘main()::<lambda()>’ to ‘const main()::<lambda()>&’


Не нашел нужного оператора присваивания.

Да и вообще, это ж все лямбды, почему я не могу их присваивать друг другу?

Дело в том, что каждое отдельное лямбда-выражение генерирует свой тип, который называется замыканием. Только компилятор знает этот тип, вы его наружу никак не можете получить. Стандарт говорит:

The type of the lambda-expression [...] is a unique, unnamed non-union class type — called the closure type.


Это легко проверить. Такой код выведет 0:

auto test = [](){};
auto test2 = [](){};
std::cout << std::is_same_v<decltype( test ), decltype( test2 )> << std::endl;


Типы действительно разные.

В целом, поэтому вместе с лямбдами всегда нужно использовать auto. Потому что ничего другого вы вместо типа физически не сможете написать. Но компилятор знает тип замыкания и сможет вывести правильный тип для переменной.

Ну и естественно, для двух рандомных классов неопределены операторы присваивания своих объектов друг другу. Поэтому код из начала и фейлится.

Differentiate thing apart. Stay cool.

#cpp11
  • 👍 37
  • ❤‍🔥 6
  • ❤ 5
  • 🔥 3
  • ⚡ 1
  • 😁 1
More from @grokaemcpp
  1. Oct 8, 2026​​Strict weak ordering #опытным На первый взгляд, всё выглядит рабочим: мы создаём 40 зака…
  2. Oct 7, 2026​​Где-то баг... #опытным Вот вам код: struct Order { int price; int id; }; int main() { st…
  3. Oct 5, 2026Откуда spurious wakeup на кондваре? #опытным У кондваров есть метод std::condition_variabl…
  4. Oct 1, 2026​​Stacktrace. Tips #опытным Чтобы полноценно работать со стандартными трейсами, нужно знат…
  5. Sep 28, 2026​​Stacktrace #опытным Одна из проблема исключений - непонятно, откуда оно прилетело. Ну да…
  6. Sep 25, 2026​​std::spanstream #опытным Радостная весть для всех, кто пользуется iostreams! В C++23 доб…
Threads Profile ViewerView any public Threads profile without an account.Open ThreadLook →Writing with AI? Make it sound human.Metric37 rewrites AI drafts so they read naturally. Free AI detector, 1,500 words free.Try Metric37 →