मैं एक समारोह के पैरामीटर (foo1
/foo2
) के संदर्भ में एक ओवरलोड समारोह (bar
) के पते को हल करने के साथ प्रयोग कर रहा हूँ का पता।SFINAE और एक ओवरलोड समारोह
struct Baz {};
int bar() { return 0; }
float bar(int) { return 0.0f; }
void bar(Baz *) {}
void foo1(void (&)(Baz *)) {}
template <class T, class D>
auto foo2(D *d) -> void_t<decltype(d(std::declval<T*>()))> {}
int main() {
foo1(bar); // Works
foo2<Baz>(bar); // Fails
}
foo1
साथ कोई परेशानी नहीं है, जो bar
के प्रकार स्पष्ट रूप से निर्दिष्ट करता है नहीं है।
main.cpp:19:5: fatal error: no matching function for call to 'foo2'
foo2<Baz>(bar); // Fails
^~~~~~~~~
main.cpp:15:6: note: candidate template ignored: couldn't infer template argument 'D'
auto foo2(D *d) -> void_t<decltype(d(std::declval<T*>()))> {}
^
1 error generated.
यह मेरी समझ है कि सी ++ अतिभारित समारोह के पते का समाधान नहीं कर सकते हैं और करते हैं:
हालांकि, foo2
है, जो सभी लेकिन bar
का एक संस्करण के लिए SFINAE के माध्यम से ही अक्षम करें, निम्न संदेश के साथ संकलित करने के लिए विफल रहता है एक ही समय में टेम्पलेट तर्क कटौती।
क्या इसका कारण है? foo2<Baz>(bar);
(या कुछ समान) बनाने के लिए कोई तरीका है संकलित?
संकलक केवल 'bar' के खिलाफ' डी * '' bar' के अन्य भार के को छान के लिए, तुलना क्या वास्तविक कटौती में '' के खिलाफ डी * तुलना करने के लिए बाद में कार्य करते निर्णय लेने की एक उप-प्रक्रिया के रूप में प्रक्रिया। यह इस ट्रेल उप-प्रक्रिया के परिणामों को फ़ंक्शन के शेष हिस्सों में बदलने की कोशिश नहीं करेगा क्योंकि यह वास्तविक कटौती में ही होता है। –
तो सवाल यह है कि "विशिष्ट फ़ंक्शन अधिभार के प्रकार को कैसे घटाया जाए?" या एक साधारण 'टेम्पलेट शून्य foo2 (शून्य (*) (टी *)) {}' पर्याप्त है? –
@MykolaBogdiuk व्यावहारिक मामला किसी भी फ़ंक्शन का समर्थन करना है जिसे 'टी * '(जो भी इसके वापसी प्रकार, उदाहरण के लिए) कहा जा सकता है, लेकिन सामान्य उत्तर अब मुझे रूचि देता है। – Quentin