2015-06-05 15 views
12

झंडा std=c++1y साथ बजना 3.5, 3.6, या 3.7, का उपयोग के साथ समारोह प्रोटोटाइप में अनुमति नहीं निम्नलिखित कोड संकलन नहीं करता है:'ऑटो' बजना

#include <iostream> 
auto foo(auto bar) { return bar; } 
int main() { 
    std::cout << foo(5.0f) << std::endl; 
} 

दिया त्रुटि है:

error: 'auto' not allowed in function prototype

मुझे g ++ 4.9 का उपयोग करके त्रुटियां नहीं हैं। क्या यह त्रुटि उत्पन्न हुई है क्योंकि क्लैंग ने अभी तक इस कार्यक्षमता को अभी तक कार्यान्वित नहीं किया है या ऐसा इसलिए है क्योंकि मुझे ऐसा करने की अनुमति नहीं है और जीसीसी किसी भी तरह से इसे अनुमति देता है?

+0

मुझे लगता है कि आपको ऐसा नहीं करना चाहिए क्योंकि आप इसे दायरे से बाहर करते हैं। – Bastien

+2

सामान्य (गैर-लैम्ब्डा) कार्यों के 'ऑटो' फ़ंक्शन पैरामीटर अवधारणाओं टीएस से एक एक्सटेंशन हैं। वे सी ++ 14 का हिस्सा नहीं हैं, जो सी ++ 1y बन गया है। – dyp

+1

बीटीडब्ल्यू, एक (एन अनौपचारिक?) [क्लैंग शाखा] (https://github.com/faisalv/clang/tree/enhanced-auto-c%2B%2B1z) है जो इसका समर्थन करता है। कुछ चर्चा [std-चर्चा मेलिंग सूची] (https://groups.google.com/a/isocpp.org/d/topic/std-discussion/PaKP8EIIlEU/discussion) पर पाई जा सकती है। मुझे नहीं पता कि उस शाखा की वर्तमान स्थिति क्या है। – dyp

उत्तर

15

हम आईएसओ सी ++ चर्चा मेलिंग से देख के रूप में: गैर lambdas के decltype(auto) parameters vs. perfect forwarding ऑटो मापदंडों concepts lite और इसलिए का हिस्सा है में नहीं सी ++ 14:

clang is correct in the sense that we don't yet have auto parameters. Concepts lite may bring those, but C++14 doesn't have them.

हम अगर हम gcc साथ -pedantic ध्वज का उपयोग प्राप्त निम्नलिखित चेतावनी:

warning: ISO C++ forbids use of 'auto' in parameter declaration [-Wpedantic] 
    auto foo(auto bar) { return bar; } 
     ^

तो यह एक एक्सटेंशन की तरह दिखता है।

रूप DYP ने कहा, polymorphic lambdas सी ++ 14 में आने से पहले की थी और ऑटो पैरामीटर, एक उदाहरण के कागज से लिया अनुमति नहीं:

// 'Identity' is a lambda that accepts an argument of any type and 
// returns the value of its parameter. 
auto Identity = [](auto a) { return a; }; 
int three = Identity(3); 
char const* hello = Identity("hello"); 

संयोग से ही कार्यक्षमता आप में लागू करना चाहते हैं है जो आपके उदाहरण।

+0

चर्चा और अतिरिक्त पैडेंटिक ध्वज को इंगित करने के लिए धन्यवाद! – coincoin

+0

@coincoin मैंने जीसीसी दस्तावेज के लिए एक लिंक जोड़ा, '-pedantic' कंपाइलर को एक्सटेंशन के लिए चेतावनियां जारी करने के लिए मजबूर करता है, मूल रूप से मानक द्वारा अनुमत कुछ भी नहीं। –

+0

@ShafikYaghmour मुझे लगता है कि वे फ़ंक्शन ओवरलोडिंग समस्या के कारण मानक नहीं बनाते हैं? ऑटो कीवर्ड फ़ंक्शन ओवरलोडिंग के साथ अस्पष्ट हो सकता है? – UnKnown

3

आप इसके बजाय किसी टेम्पलेट का उपयोग कर सकते हैं:

template<class A> 
A foo(A bar) { return bar; } 

ऑटो केवल जब संकलक संदर्भ से प्रकार यह मान सकते हैं अनुमति दी है।

1

कंपाइलर संदर्भ से प्रकार का अनुमान नहीं लगा सकता है।

क्या

template<typename Y> 
Y foo(Y bar){return bar;} 

कर साथ कुछ गड़बड़ है और आप मान द्वारा bar से गुजरना होगा?

अपने मामले में आप अनुगामी वापसी प्रकार सिंटैक्स का उपयोग कर सकते हैं:

auto foo(auto bar) -> decltype(bar)

+1

@ बाथशेबा 'ऑटो' पैरामीटर सूची में अनुमति नहीं देते हैं (लेकिन सी ++ 14 में '-> 'के बिना वापसी प्रकार ऑटो की अनुमति है) –

+0

मुझे समझ में नहीं आता है। फ़ंक्शन पैरामीटर के रूप में पारित होने पर कंपाइलर प्रकार का अनुमान क्यों नहीं लगा सकता है? –

7

हालांकि अपने विशिष्ट वाक्यविन्यास सी ++ 14 के लिए यह नहीं किया, एक ऐसी ही विकल्प जो किया है:

static auto foo = [](auto bar) { return bar; }; 

जो मूल रूप से एक ही बात को प्राप्त होता है।

+0

एमएम, क्या आप कृपया समझा सकते हैं कि क्यों 'स्थिर ऑटो'? – UnKnown

+1

@UnKownown का अर्थ है 'foo' का नाम * आंतरिक लिंक * है, यानी यह अन्य इकाइयों से नाम से सुलभ नहीं है। यह आकस्मिक अपरिभाषित व्यवहार को रोकता है अगर उदाहरण के लिए एक और फ़ाइल 'int foo = 5;' जाती है। यह बाहरी लिंकेज का उपयोग करने के लिए बहुत अधिक समझ नहीं लेगा क्योंकि आप लैम्ब्डा (वास्तविक परिभाषा के अलावा) के लिए एक घोषणा नहीं लिख सकते हैं, इसलिए कोई अन्य इकाई वैसे भी इसका सही तरीके से उपयोग करने में सक्षम नहीं होगी। –

संबंधित मुद्दे