爲什麼我不能叫拉姆達遞歸,如果我把它寫成:
auto a = [&]
{
static int i = 0; i++;
std::cout << i << std::endl;
if (i<10)
a(); //recursive call
};
它給出編譯錯誤(ideone):
prog.cpp:8:18: error: '((const main()::<lambda()>*)this)->main()::<lambda()>::a' cannot be used as a function
prog.cpp: In function 'int main()':
prog.cpp:9:9: error: variable 'auto a' with 'auto' type used in its own initializer
錯誤是什麼意思?
我明白其中的道理,爲什麼我不能這樣寫:
auto i=i+1; //error: unable to deduce 'auto' from '<expression error>'
我們不能寫,因爲i
的類型必須推斷,從它的初始化,這意味着無法被推斷,如果該類型i
本身出現在初始化中(ideone)。但是在lambda的情況下它又有什麼關係?如果我沒有錯,lambda的類型由它的參數和返回類型決定;如果它不返回任何內容,則不依賴於主體(在這種情況下,返回類型推導爲void
,而不考慮lambda主體中的其他語句)。
無論如何,我得到了一個解決辦法,我可以使用std::function
代替爲:
std::function<void()> a = [&]
{
static int i = 0; i++;
std::cout << i << std::endl;
if (i<10)
a();
};
它編譯罰款(ideone)。但我仍然很想知道爲什麼auto
版本不能編譯的原因。
我認爲這個問題與你最終隱式捕獲'a'有關,因爲'a'本身最終會成爲'a'的成員,因此會無限遞歸。 – Flexo
@awoodland:這是什麼意思?請詳細說明。 – Nawaz
lambda的類型也取決於捕獲,我懷疑這是問題。如果你不使用'a',那麼編譯器不關心,但是當你這樣做的時候它不知道要使用什麼類型的對象。 –