आपके प्रश्न के बारे में स्पष्टीकरण देने के लिए कुछ चीजें हैं। जिनमें से पहला लैम्ब्डा क्या है?
एक लैम्ब्डा अभिव्यक्ति एक साधारण अभिव्यक्ति है जिससे संकलक एक अद्वितीय प्रकार उत्पन्न करेगा जिसे नामित नहीं किया जा सकता है, और साथ ही यह प्रकार का एक उदाहरण उत्पन्न करेगा। जब आप लिखें: [](int i) { std::cout << i; }
संकलक उत्पन्न होगा आपको लगता है कि के लिए एक प्रकार मोटे तौर पर है:
struct __lambda_unique_name {
void operator()(int i) const { std::cout << i; }
};
आप देख सकते हैं, यह है नहीं एक समारोह है, लेकिन एक प्रकार है कि एक const
सदस्य समारोह के रूप में operator()
लागू करता है। यदि लैम्ब्डा ने कोई कैप्चर किया है, तो संकलक मूल्य/संदर्भों को कैप्चर करने के लिए कोड उत्पन्न करेगा।
एक कोने मामले के रूप में, इसके बाद के संस्करण है, जहां कोई राज्य पर कब्जा कर लिया जा रहा है की तरह lambdas के लिए, भाषा एक सूचक को लैम्ब्डा प्रकार से एक रूपांतरण operator()
के हस्ताक्षर (ऋण this
हिस्सा) के साथ कार्य करने के लिए के लिए अनुमति देता , इसलिए लैम्ब्डा ऊपर परोक्ष एक सूचक में बदला जा सकता int
ले रहे हैं और कुछ भी नहीं लौटने कार्य करने के लिए:
void (*f)(int) = [](int i) { std::cout << i; }
अब जब कि मूल बातें कहा गया है, अपने कोड में आप इस लैम्ब्डा है:
auto f = [x,y](double (func)(int)) -> double {func(0); return 0.0;};
फ़ंक्शंस के लिए पैरामीटर के नियम (जो लैम्बडास पर भी लागू होते हैं) यह निर्धारित करते हैं कि कोई तर्क फ़ंक्शन प्रकार का नहीं हो सकता है, इसलिए लैम्ब्डा के लिए तर्क कार्य करने के लिए पॉइंटर को डीक करता है (उसी तरह से टाइप सरणी का तर्क बाद में आप एक लैम्ब्डा एक तर्क के रूप में एक पर कब्जा किया है कि पारित करने के लिए कोशिश कर रहे हैं पर
auto f = [x,y](double (*func)(int)) -> double {func(0); return 0.0;};
: एक सूचक प्रकार के क्षय)। चूंकि एक कैप्चर होता है, विशेष नियम लागू नहीं होता है और लैम्ब्डा आपके द्वारा देखे गए कंपाइलर त्रुटि को उत्पन्न करने के लिए एक सूचक को परिवर्तनीय नहीं है।
वर्तमान मानक में आप दो तरीकों से जा सकते हैं। आप हस्ताक्षर से प्रतिदेय इकाई का सही प्रकार दूर करने के लिए टाइप-विलोपन का उपयोग कर सकते हैं:
auto f = [x,y](std::function<double(int)> func) -> double {func(0); return 0.0;};
क्योंकि एक std::function<double(int)>
उचित हस्ताक्षर के साथ किसी भी प्रतिदेय इकाई के साथ प्रारंभ किया जा सकता है, इस में lambdas स्वीकार करेंगे नीचे दिए गए कोड, टाइप-एरर की लागत पर जो आमतौर पर एक गतिशील आवंटन और गतिशील प्रेषण का तात्पर्य है।
वैकल्पिक रूप से, आप सिंटैक्टिक चीनी छोड़ सकते हैं और पहले लैम्ब्डा को मैन्युअल रूप से समकक्ष रोल कर सकते हैं, लेकिन इसे सामान्य बना सकते हैं।
struct mylambda {
template <typename F>
double operator()(F fn) const {
fn(0); return 0.0;
}
} f;
// then use the non-lambda as you tried:
f([x](int i) -> double {return 0.0;});
अंत में, यदि आपके पास पर्याप्त रोगी हैं, आप के लिए सी ++ 14, जहां (संभवत:, यह अभी तक नहीं किया गया है इंतज़ार कर सकते हैं: इस मामले में, जहां लैम्ब्डा सरल है में यह एक वैध विकल्प हो सकता है पुष्टि की) बहुरूपी lambdas जो ऊपर वर्ग के निर्माण को आसान बनाने के लिए समर्थन किया जाएगा:
auto f = [](auto fn) { fn(0.0); return 0.0; } // unrolls to 'mylambda' above
कैप्चरिंग लैम्ब्डा फ़ंक्शन पॉइंटर्स में परिवर्तनीय नहीं हैं –
क्यों नहीं 'constexpr'? 'auto' एक संकलन-समय सुविधा है वैसे भी ... – user2485710
@AndyProwl क्या? 10 मिनट के भीतर आप से कोई विस्तृत जवाब नहीं है? चलो, आप हमें यहां बहुत मेहनत करते हैं, और आपने दिन के लिए भी दोबारा तैयार नहीं किया है ;-) – TemplateRex