2011-12-30 12 views
6

यदि आपको डी में निम्नलिखित C++ कोड को फिर से लिखना आवश्यक है, तो आप इसे कैसे करेंगे?सी ++ कोड को फिर से लिखना कैसे है जो डी में परिवर्तनीय उपयोग करता है?

struct A{ 

    const S* _s; 
    B _b; 
    C _c; 
    mutable C _c1, _c2; 

    A(const B& b, const C& c, const S* s){ /*...*/ } 

    void compute(const R& r) const 
    { 
     //... 
     _c1 = ... 
     _c2 = ... 
    } 
}; 

डी mutable नहीं है, और, मेरे अनुभव के आधार पर, यह शायद ही कभी सी में प्रयोग किया जाता है ++। लेकिन, मानते हैं कि mutable का सही कारण यहां उपयोग किया जाता है, डी में मेरे विकल्प क्या हैं?

+0

यह एक ऐसी ही सवाल यह है: http://stackoverflow.com/questions/4219600/logical-const-in-d –

उत्तर

3

आपके पास तीन विकल्प इस से निपटने के लिए:

  1. const को कास्ट करें। यह कंपाइलर को बंद कर देगा, लेकिन इस बात की कोई गारंटी नहीं है कि आपका कोड इरादे के अनुसार काम करेगा। विशेष रूप से, यदि आप एक ही ऑब्जेक्ट पर एक ही ऑब्जेक्ट पर एकाधिक फ़ंक्शन से कॉल करते हैं तो आप डेटा दौड़ की करुणा पर हैं।

  2. परिवर्तनशील वस्तुओं स्टोर करने के लिए एक बाहरी डेटा संरचना का उपयोग करें:

    struct A 
    { 
        static C[const(A)*] _c1s, _c2s; 
    
        void compute(ref const(R) r) const 
        { 
         _c1s[&this] = ... 
         _c2s[&this] = ... 
        } 
    } 
    

    मैं बाहरी हैश तालिका की कुंजी के रूप &this उपयोग कर रहा हूँ, लेकिन आप शायद अद्वितीय ID किसी प्रकार का उपयोग कर बंद बेहतर होगा । यह एक बहुत बदसूरत और मुश्किल समाधान है। मैं इसे नापसंद करता हूं। साथ ही, ध्यान दें कि हैश टेबल थ्रेड-लोकल हैं, इसलिए एक ही ऑब्जेक्ट के अलग-अलग धागे पर अलग-अलग मान होंगे। यह आपके विशेष आवेदन के लिए वांछनीय हो सकता है या नहीं भी हो सकता है।

  3. Rethink कैसे आप डी

    डी में में const उपयोग करते हैं, const सकर्मक और बिटवाइज़ अर्थात तार्किक स्थिरांक समर्थित नहीं है। इसका उद्देश्य समवर्ती साझा डेटा लिखने के खिलाफ गारंटी देना है। भले ही आपका कोड तर्कसंगत रूप से सही हो, फिर भी दो धागे उसी ऑब्जेक्ट पर compute पर कॉल करने का प्रयास करते हैं, इसलिए डी इसे अस्वीकार करता है और कोई कानूनी भाग नहीं देता है (mutable)।

    अनिवार्य रूप से, आप const के रूप में कार्य को चिह्नित केवल जब वे बिटवाइज़ स्थिरांक हैं चाहिए।

    इसका नतीजा यह है कि आपको सी ++ में const डी में बहुत कम उपयोग करना चाहिए क्योंकि आपको बिटिकल कॉस्ट की आवश्यकता है जो आपको लॉजिकल कॉन्स की आवश्यकता से बहुत कम है।

    bool equal(T)(T lhs, T rhs) { return lhs == rhs; } 
    

    सूचना है कि मैं const के रूप में चिह्नित नहीं किया है समारोह पैरामीटर:

    उदाहरण के लिए, एक सरल (व्यर्थ) सामान्य equal समारोह है कि आपको बताता है कि दो वस्तुओं के बराबर हैं पर विचार करें। यह उद्देश्य पर है। समानता के लिए परीक्षण बिटवाईड कॉन्स की आवश्यकता नहीं है - इसे केवल तार्किक आधार की आवश्यकता होती है, इसलिए ऑब्जेक्ट्स पर डी का स्तर लागू करना अनिवार्य रूप से प्रतिबंधित होगा।

    जैसा कि jA_cOp कहता है, डी समुदाय बेहतर या बदतर के लिए डी में लॉजिकल कॉन्स के लिए कोई जगह नहीं देखता है। समस्या तब उत्पन्न होती है जब आप सी ++ के कॉन्स जैसे डीएस कॉन्स का उपयोग करने का प्रयास करते हैं। वे वही नहीं हैं, इसलिए उन्हें उसी तरह प्रयोग न करें! यदि किसी भी कार्य को किसी भी कार्य को लॉजिकल कॉन्स के उपयोग की आवश्यकता हो सकती है तो उन्हें बिटवाईड कॉन्स के रूप में चिह्नित न करें!

+0

आपके 'बराबर()' के समान है, मैंने अपने अधिकांश फ़ंक्शन पैरामीटर 'const' को बनाया है और मुझे अब तक कोई समस्या नहीं है। क्या ऐसा इसलिए है क्योंकि 'const' अभी भी टूटा हुआ है? – Arlen

+0

मुझे लगता है कि कॉन्स ज्यादातर काम कर रहा है। हालांकि, मुझे लगता है कि फोबोस में कुछ चीजें सही नहीं हैं (मुझे लगता है) और पोस्ट ब्लिट कन्स्ट्रक्टर के साथ एक बड़ा मुद्दा है, लेकिन मुझे लगता है कि अधिकांश कास्ट काम कर रहा है। –

+0

तो, डी (सी ++ में) जोड़ते समय बड़ी आजादी होने की बजाय, डी में यह विपरीत है; पैरामीटर बनाने के लिए यह अधिक प्रतिबंधक है? –

6

डी immutable एक अपरिवर्तनीय संदर्भ (जैसे this एक अपरिवर्तनीय सदस्य फ़ंक्शन में संदर्भ) दिया गया है, तो सभी फ़ील्ड अपरिवर्तनीय हैं। डी const में इसके आसपास कोई रास्ता नहीं है केवल डी में विस्थापन योग्य और अपरिवर्तनीय डेटा को बांधने के लिए मौजूद है, लेकिन चूंकि अपरिवर्तनीय रूप से कॉन्स्ट में परिवर्तनीय है, इसलिए इसे भी संक्रमित होना चाहिए। एक बार जब आप अपरिवर्तनीय (या कॉन्स) जाते हैं, तो आप वापस नहीं जा सकते हैं।

लाभ कई हैं: अपरिवर्तनीय डेटा को धागे में सुरक्षित रूप से साझा किया जा सकता है, यदि वांछनीय हो तो रोम में रखा जा सकता है, और इसके साथ तर्क करना आसान है।

बेहतर या बदतर के लिए डी में लॉजिकल कॉन्स के लिए बस कोई जगह नहीं है।

+0

ताकि आप सुझाव दे रहे हैं कि मैं बनाने के '_c1',' _c2', 'गणना () 'और 'ए' गैर-कॉन्स के सभी संदर्भ? – Arlen

+0

@ आर्लन, अगर आपको अपनी विधि में 'इस' ऑब्जेक्ट को म्यूट करने की आवश्यकता है तो यह आपकी एकमात्र पसंद है। ध्यान दें कि आप अभी भी कहीं और संग्रहीत डेटा को म्यूट कर सकते हैं (डुह), जिसे आप कभी-कभी लीवरेज कर सकते हैं जब इरादा कैश उद्देश्यों के लिए म्यूटेबल डेटा का उपयोग करना है। लेकिन कैश के साथ सामान्य केस (हैश मैप इत्यादि) में ऐसी बाहरी कैशिंग बदसूरत है? ईडब्ल्यू!) और एक अनसुलझा समस्या बनी हुई है। –

4

लघु संस्करण; आप डिजाइन द्वारा नहीं कर सकते हैं।

लंबे संस्करण, डी के डिजाइनरों ने निष्कर्ष निकाला (कुछ महाकाव्य बहस के बाद) कि म्यूटेबल के लाभ डाउनसाइड्स से अधिक हो गए हैं। (देखें: विवरण में से कुछ, अन्य reaons के कई एक इरादे से प्रेरित हैं के लिए jA_cOp के जवाब समवर्ती प्रोग्रामिंग और कम बदसूरत की वहाँ तर्क बनाने के लिए।)

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