2012-12-02 18 views
6

सी ++ 11 किसी भी तरह gcc में में एक एक समारोह (नहीं एक वर्ग विधि) const के रूप में कह रही है कि यह शुद्ध है और वैश्विक स्मृति लेकिन केवल अपने तर्कों का उपयोग नहीं करता निशान कर सकते हैं?शुद्ध कार्यों सी ++ 11

मैंने gcc के __attribute__((const)) को आजमाया है और यह ठीक है जो मैं चाहता हूं। लेकिन यह किसी भी संकलन समय त्रुटि उत्पन्न नहीं करता है जब फ़ंक्शन में वैश्विक मेमोरी छूती है।

संपादित करें 1

कृपया सावधान हो। मेरा मतलब शुद्ध कार्य है। निरंतर कार्य नहीं। जीसीसी की विशेषता थोड़ा उलझन में है। शुद्ध कार्य केवल उनके तर्कों का उपयोग करते हैं।

+0

और न ही आपका क्या मतलब है, लेकिन आपने कोशिश की है कि 'constexpr' –

+0

ऐसा नहीं है। मेरा मतलब है शुद्ध शुद्ध नहीं है। जीसीसी के गुण थोड़ा उलझन में हैं। – Cartesius00

+1

मुझे लगता है कि आपको अपने प्रश्न को फिर से भरना होगा, क्योंकि आपके पास सही विशेषता है। यह आपके द्वारा की जाने वाली चेतावनी का उत्पादन नहीं करता है - कम से कम जब आपका प्रश्न अंकित मूल्य पर लेता है। –

उत्तर

4

क्या आप constexpr खोज रहे हैं? यह संकलक को बताता है कि संकलन समय पर फ़ंक्शन का मूल्यांकन किया जा सकता है। constexpr फ़ंक्शन में शाब्दिक रिटर्न और पैरामीटर प्रकार होना चाहिए और शरीर में केवल स्थिर आवेषण, टाइपपीफ, घोषणाओं और निर्देशों का उपयोग करके और एक रिटर्न स्टेटमेंट हो सकता है। निरंतर अभिव्यक्ति में constexpr फ़ंक्शन को कॉल किया जा सकता है।

constexpr int add(int a, int b) { return a + b; } 

int x[add(3, 6)]; 

__atribute__((const)) के अर्थ को देखा करने के बाद, इस सवाल का जवाब ++ नहीं, तुम मानक सी के साथ ऐसा नहीं कर सकते है। constexpr का उपयोग करना एक ही प्रभाव प्राप्त करेगा, लेकिन केवल कार्यों के सीमित सेट पर ही। इन अनुकूलन को स्वयं बनाने से संकलक को रोकना कुछ भी नहीं है, हालांकि, जब तक संकलित प्रोग्राम एक ही तरीके से व्यवहार करता है (जैसा कि नियम है)।

+0

नहीं, नहीं, मेरा मतलब शुद्ध कार्य है। कृपया मुझे संपादित करें देखें। – Cartesius00

+0

@ मार्टिन और अधिक –

+0

धन्यवाद। विशेषता 'constexpr' लगभग बेकार है। शायद चलो थोड़ा और इंतजार करें। शायद कुछ अन्य 'gcc'-विशिष्ट विशेषता मदद कर सकती है। – Cartesius00

0

का उपयोग कर सिर्फ मानक सी ++ 11:

namespace g{ int x; } 

constexpr int foo() 
{ 
    //return g::x = 42; Nah, not constant 
    return 42;  // OK 
} 

int main() 
{} 

यहाँ

एक और उदाहरण है:

constexpr int foo(int blah = 0) 
{ 
    return blah + 42;  // OK 
} 

int main(int argc, char**) 
{ 
    int bah[foo(2)];   // Very constant. 
    int const troll = foo(argc); // Very non-constant. 
} 

जीसीसी के __attribute__(const) के अर्थ के रूप में GNU compiler docs है & hellip में प्रलेखित है;

कई फ़ंक्शन उनके तर्कों को छोड़कर किसी भी मूल्य की जांच नहीं करते हैं, और वापसी मूल्य को छोड़कर कोई प्रभाव नहीं पड़ता है। असल में यह pure विशेषता से थोड़ा अधिक सख्त वर्ग है, क्योंकि फ़ंक्शन को वैश्विक मेमोरी पढ़ने की अनुमति नहीं है।

कोई इसका मतलब यह ले सकता है कि फ़ंक्शन परिणाम केवल तर्कों पर निर्भर होना चाहिए, और फ़ंक्शन का कोई साइड इफेक्ट नहीं होना चाहिए।

यह, की तुलना में सी ++ 11 constexpr, जो समारोह inline बनाता कार्यों की एक अधिक सामान्य वर्ग की अनुमति देता है शाब्दिक प्रकार को तर्क और समारोह परिणाम प्रतिबंधित करता है, और एक ही करने के लिए समारोह शरीर के "सक्रिय" बयान को प्रतिबंधित करता है return बयान है, जहां (सी ++ 11 §7.1.5/3)

- हर निर्माता कॉल और अंतर्निहित वापसी मान (6.6.3, 8.5) आरंभ में इस्तेमाल किया रूपांतरण एक में अनुमति दी उन में से एक हो जाएगा निरंतर अभिव्यक्ति (5.1 9)

उदाहरण के तौर पर, constexprsin फ़ंक्शन बनाने के लिए यह मुश्किल है (मुझे असंभव नहीं लगता है, लेकिन मुश्किल)।

लेकिन परिणाम मामलों की पवित्रता केवल दो पार्टियों:

  • जब शुद्ध होने के लिए जाना जाता है, संकलक ज्ञात परिणामों के साथ कॉल छिपाना कर सकते हैं।
    यह ज्यादातर मैक्रो-जेनरेट कोड का अनुकूलन है। समान उप-अभिव्यक्तियों की मूर्खतापूर्ण पीढ़ी से बचने के लिए मैक्रोज़ को inline फ़ंक्शंस के साथ बदलें।

  • जब शुद्ध होने के लिए जाना जाता है, तो प्रोग्रामर पूरी तरह से कॉल को हटा सकता है।
    यह उचित दस्तावेज का मामला है। :-)

तो उदासी की शुद्धता व्यक्त करने के लिए एक तरीका तलाशने की बजाय भाषा में sin, मेरा सुझाव है कि मैक्रोज़ के माध्यम से कोड जनरेशन से बचें, और इस तरह के दस्तावेज़ों को शुद्ध कार्य करें।

और उन कार्यों के लिए constexpr का उपयोग करें जहां यह व्यावहारिक रूप से संभव है (दुर्भाग्य से, दिसंबर 2012 तक नवीनतम विज़ुअल सी ++ कंपाइलर अभी तक constexpr का समर्थन नहीं करता है)।


the relationship between pure and constexpr के बारे में पिछले SO प्रश्न हैं। मुख्य रूप से, प्रत्येक constexpr फ़ंक्शन शुद्ध है, लेकिन इसके विपरीत नहीं है।

+0

नहीं, नहीं, मेरा मतलब शुद्ध कार्य है, निरंतर कार्य नहीं। – Cartesius00

+0

@ मार्टिन: अच्छी तरह से दो समस्याएं उत्पन्न करने के लिए अस्पष्ट विचार होने के कारण आपकी समस्या के विवरण के जवाब को कम करने के लिए थोड़ा मुश्किल है। "थोड़ा" कठोर? क्षमा करें, मेरा मतलब था, * काफी * कठोर। चीज़। –

+0

मेरी समस्या? प्रश्न उन लोगों के लिए था जो 'शुद्ध' और जीसीसी के गुणों के अर्थ को जानते थे। – Cartesius00