कंस्ट्रक्टर इनिशियलाइज़र में एक सदस्य सरणी को आरम्भ करना


99
class C 
{
public:
 C() : arr({1,2,3}) //doesn't compile
{}
    /*
    C() : arr{1,2,3} //doesn't compile either
{}
    */
private:
 int arr[3];
};

मेरा मानना ​​है कि कारण यह है कि सरणियों को केवल =सिंटैक्स के साथ आरंभ किया जा सकता है , अर्थात:

int arr[3] = {1,3,4};

प्रशन

  1. मैं वह कैसे कर सकता हूं जो मैं करना चाहता हूं (वह है, एक कंस्ट्रक्टर में एक सरणी को इनिशियलाइज़ करना) ( शरीर में तत्वों को असाइन नहीं करना)। क्या यह भी संभव है?
  2. क्या C ++ 03 मानक ctor initializers में एग्रीगेट (सरणियों सहित) को इनिशियलाइज़ करने के बारे में कुछ खास कहता है? या उपरोक्त कोड की अवैधता कुछ अन्य नियमों का एक समूह है?
  3. क्या C ++ 0x इनिशियल लिस्ट समस्या का समाधान करता है?

PS कृपया वैक्टर का उल्लेख न करें, बढ़ावा :: सरणियों, और सरणियों के लिए उनकी श्रेष्ठता, जो मैं अच्छी तरह से जानता हूं।


क्या आप भी निश्चित आकार के सरणियों को बढ़ावा देने के अस्तित्व के बारे में जानते हैं, जो निर्माणकर्ता प्रदान करते हैं?
बेनोइट

2
@ Benoît: मैं हूँ। लेकिन मुझे सादे सरणियों के बारे में जानने की आवश्यकता है :)
अर्मेन Tsirunyan

जवाबों:


56
  1. मैं वह कैसे कर सकता हूं जो मैं करना चाहता हूं (वह है, एक कंस्ट्रक्टर में एक सरणी को इनिशियलाइज़ करना) (शरीर में तत्वों को असाइन नहीं करना)। क्या यह भी संभव है?

हाँ। यह एक ऐसी संरचना का उपयोग कर रहा है जिसमें एक सरणी है। आप कहते हैं कि आप पहले से ही इस बारे में जानते हैं, लेकिन तब मैं इस सवाल को नहीं समझता। इस तरह, आप कर शरीर में कार्य बिना निर्माता में एक सरणी को प्रारंभ,। ये क्या boost::arrayकरता है

क्या C ++ 03 मानक ctor initializers में एग्रीगेट (सरणियों सहित) को इनिशियलाइज़ करने के बारे में कुछ खास कहता है? या उपरोक्त कोड की अवैधता कुछ अन्य नियमों का एक समूह है?

एक मेम-इनिलाइज़र प्रत्यक्ष इनिशियलाइज़ेशन का उपयोग करता है। और खण्ड 8 के नियम इस प्रकार की मनाही करते हैं। मैं निम्नलिखित मामले के बारे में बिल्कुल निश्चित नहीं हूं, लेकिन कुछ संकलक इसे अनुमति देते हैं।

struct A {
  char foo[6];
  A():foo("hello") { } /* valid? */
};

देखें इस जीसीसी पीआर अधिक जानकारी के लिए।

क्या C ++ 0x इनिशियल लिस्ट समस्या का समाधान करता है?

हाँ, वो करते हैं। हालाँकि आपका सिंटैक्स अमान्य है, मुझे लगता है। सूची प्रारंभ करने के लिए आपको सीधे ब्रेसिज़ का उपयोग करना होगा

struct A {
  int foo[3];
  A():foo{1, 2, 3} { }
  A():foo({1, 2, 3}) { } /* invalid */
};

जब मैंने लिखा: char * const foo[6];कक्षा सदस्य। यह C + 11 में संकलन करने के लिए इनिशलाइज़र की आवश्यकता होती है।
16

33

C ++ 98 किसी भी चीज़ के लिए (लेकिन गैर-पीओडी तत्वों के लिए, मूल्य-आरंभीकरण) सरणी के लिए एक प्रत्यक्ष वाक्यविन्यास प्रदान नहीं करता है। उसके लिए आप बस लिखें C(): arr() {}

मुझे लगता है कि रोजर पाटे C ++ 0x कुल एकत्रीकरण की कथित सीमाओं के बारे में गलत है, लेकिन मैं इसे देखने या इसकी जांच करने के लिए बहुत आलसी हूं, और यह कोई फर्क नहीं पड़ता, क्या यह करता है? EDIT : रोजर "सी ++ 03" के बारे में बात कर रहा था, मैंने इसे "सी ++ 0x" के रूप में गलत बताया। क्षमा करें, रोजर। ☺

आपके वर्तमान कोड के लिए C ++ 98 वर्कअराउंड को एरे में लपेटना है structऔर इसे उस प्रकार के स्थिर स्थिर से इनिशियलाइज़ करना है। डेटा को वैसे भी कहीं रहना होता है। कफ से यह इस तरह दिख सकता है:

class C 
{
public:
    C() : arr( arrData ) {}

private:
     struct Arr{ int elem[3]; };
     Arr arr;
     static Arr const arrData;
};

C::Arr const C::arrData = {{1, 2, 3}};

0x की क्या सीमाएँ हैं?

@Roger: "एग्रीग्रेट इनिशियलाइज़ेशन ... एक कॉर्टियर इनिशियलाइज़र में फिट नहीं होता है"। बस C ++ 0x ड्राफ्ट N3126 की जांच कर रहा है , izer12.5.2 / 1 में एक मेम-इनिशियलाइज़र का सिंटैक्स , जिसमें एक लट - इनिट -सूची का उपयोग करना शामिल है ।
चीयर्स एंड हीथ। - अल्फ

6
मेरे वाक्य के पहले दो शब्द C ++ 03 में हैं, ...

8

युक्ति:

template<class T, size_t N>
struct simple_array { // like std::array in C++0x
   T arr[N];
};


class C : private simple_array<int, 3> 
{
      static simple_array<int, 3> myarr() {
           simple_array<int, 3> arr = {1,2,3};
           return arr;
      }
public:
      C() : simple_array<int, 3>(myarr()) {}
};

3
  1. दुर्भाग्य से नहीं।
  2. आप केवल उस तरीके से नहीं कर सकते जैसा आप चाहते हैं, क्योंकि यह व्याकरण (अधिक नीचे) की अनुमति नहीं है। आप केवल ctor जैसी इनिशियलाइज़ेशन का उपयोग कर सकते हैं, और, जैसा कि आप जानते हैं, कि सरणियों में प्रत्येक आइटम को इनिशियलाइज़ करने के लिए उपलब्ध नहीं है।
  3. मेरा ऐसा मानना ​​है, क्योंकि वे कई उपयोगी तरीकों से बोर्ड भर में आरंभीकरण को सामान्य करते हैं। लेकिन मुझे विवरणों पर यकीन नहीं है।

C ++ 03 में, एग्रीगेट इनिशियलाइज़ेशन केवल नीचे के रूप में सिंटैक्स के साथ लागू होता है, जो एक अलग स्टेटमेंट होना चाहिए और एक कॉइन इनिशियलाइज़र में फिट नहीं होता है।

T var = {...};


-3

आप अपने निर्माता में ints की एक सरणी init करना चाहते हैं? इसे एक स्थिर सरणी की ओर इंगित करें।

class C 
{
public:
    int *cArray;

};

C::C {
    static int c_init[]{1,2,3};
    cArray = c_init;
}

2
यह एक बुरा विचार है, क्योंकि यदि आप उस सरणी को बदलते हैं, तो यह उस वर्ग के सभी उदाहरणों के लिए बदल जाता है।
मर्त्य
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.