lvalue
ラムダクロージャーは常にrvalue
関数パラメーターとして渡すことができることがわかりました。
次の簡単なデモをご覧ください。
#include <iostream>
#include <functional>
using namespace std;
void foo(std::function<void()>&& t)
{
}
int main()
{
// Case 1: passing a `lvalue` closure
auto fn1 = []{};
foo(fn1); // works
// Case 2: passing a `lvalue` function object
std::function<void()> fn2 = []{};
foo(fn2); // compile error
return 0;
}
ケース2は標準の動作です(std::function
デモ目的で単にを使用しましたが、他のタイプも同じように動作します)。
ケース1はどのように、そしてなぜ機能するのですか?fn1
関数が返された後の閉鎖の状態はどうですか?
std::function
ラムダから推定できないのか」ということでした。プログラムはのテンプレート引数を推定しようとしないstd::function
ので、暗黙の変換に問題はありません。
std::function
ラムダクロージャを受け入れる非明示的なコンストラクタがあるため、暗黙の変換があります。ただし、リンクされた質問の状況では、のテンプレートのインスタンス化はstd::function
ラムダ型から推測できません。(例えば、std::function<void()>
から構成することができる[](){return 5;}
、それがvoid以外の戻り値の型を持っているにもかかわらず。
fn1
暗黙的に変換されるstd::function
の中でfoo(fn1)
。その一時的な関数は右辺値です。