ডিফল্ট, মান এবং শূন্য সূচনা জগাখিচুড়ি


89

আমি মান- এবং ডিফল্ট- এবং শূন্য-সূচনা সম্পর্কে খুব বিভ্রান্ত। এবং বিশেষত যখন তারা বিভিন্ন মানের সি ++ 03 এবং সি ++ 11 (এবং সি ++ 14 ) জন্য সন্ধান করে।

আমি উদ্ধৃত করছি এবং সত্যিই ভাল উত্তরটি প্রসারিত করার চেষ্টা করছি মান- / ডিফল্ট- / জিরো- উদ্যোগ সি ++ 98 এবং সি ++ 03 এটিকে আরও সাধারণ করে তোলার জন্য এটি যদি প্রচুর ব্যবহারকারীদের সাহায্য করতে পারে তবে কেউ যদি পূরণ করতে সহায়তা করতে পারে ফাঁকগুলি যখন প্রয়োজন তখন একটি ভাল ওভারভিউ আছে?

সংক্ষেপে উদাহরণ দ্বারা সম্পূর্ণ অন্তর্দৃষ্টি:

কখনও কখনও নতুন অপারেটরের ফিরে আসা মেমরিটি আরম্ভ করা হবে, এবং কখনও কখনও এটি নির্ভর করে না আপনি যে ধরণের নতুন আপ করছেন তা কোনও পিওডি (সাধারণ পুরানো ডেটা) , বা যদি এটি এমন কোনও শ্রেণি যেখানে পিওড সদস্য রয়েছে এবং এটি ব্যবহার করছে সংকলক উত্পাদিত ডিফল্ট নির্মাণকারী।

  • ইন সি ++ 1998 : আরম্ভের 2 ধরনের আছে zero- এবং ডিফল্ট-আরম্ভের
  • ইন সি ++ 2003 আরম্ভের, 3 য় টাইপ মান-আরম্ভের যোগ করা হয়েছিল।
  • ইন সি ++ 2011 / সি ++ 2014 শুধুমাত্র তালিকা-আরম্ভের যোগ করা হয়েছিল এবং জন্য নিয়ম value- / default- / জিরো-আরম্ভের একটু পরিবর্তন করেছেন।

ধরে নিন:

struct A { int m; };                     
struct B { ~B(); int m; };               
struct C { C() : m(){}; ~C(); int m; };  
struct D { D(){}; int m; };             
struct E { E() = default; int m;}; /** only possible in c++11/14 */  
struct F {F(); int m;};  F::F() = default; /** only possible in c++11/14 */

একটি সি ++ 98 সংকলকটিতে, নিম্নলিখিতটি হওয়া উচিত :

  • new A - অনির্দিষ্ট মান ( Aপিওড হয়)
  • new A()- শূন্য-সূচনা
  • new B - ডিফল্ট কনস্ট্রাক্ট ( অবিচ্ছিন্ন B::m, Bনন-পিওডি হয়)
  • new B()- ডিফল্ট কনস্ট্রাক্ট ( B::mঅবিচ্ছিন্ন)
  • new C - ডিফল্ট কনস্ট্রাক্ট ( C::mশূন্য-সূচনা হয়, Cনন-পিওডি হয়)
  • new C()- ডিফল্ট নির্মাণ ( C::mশূন্য-সূচনা)
  • new D - ডিফল্ট কনস্ট্রাক্ট ( অবিচ্ছিন্ন D::m, Dনন-পিওডি হয়)
  • new D()- ডিফল্ট নির্মাণ? ( D::mঅবিচ্ছিন্ন)

একটি C ++ 03 কনফর্মেন্ট কম্পাইলারে জিনিসগুলি এমনভাবে কাজ করা উচিত:

  • new A - অনির্দিষ্ট মান ( Aপিওড হয়)
  • new A() - মান-ইনিশিয়ালাইজেশন A, যা এটি একটি শূন্য-সূচনা কারণ এটি একটি পিওডি।
  • new B - ডিফল্ট-ইনিশিয়ালাইজগুলি ( অবিচ্ছিন্ন পাতা ছেড়ে দেয় B::m, Bনন-পিওডি হয়)
  • new B() - মান-প্রাথমিককরণ Bযা ডিফল্ট কর্টর ব্যবহারকারী-সংজ্ঞায়নের বিপরীতে সংকলক তৈরি হওয়ার কারণে সমস্ত ক্ষেত্র শূন্য-সূচনা করে।
  • new C - ডিফল্ট-আরম্ভ হয় C, যা ডিফল্ট কর্টর বলে। ( C::mশূন্য-ইনিশিয়েলড, Cনন-পিওডি)
  • new C() - মান-প্রাথমিককরণ C, যাকে ডিফল্ট কর্টর বলে। ( C::mশূন্য-সূচনা হয়)
  • new D - ডিফল্ট কনস্ট্রাক্ট ( অবিচ্ছিন্ন D::m, Dনন-পিওডি হয়)
  • new D() - মান-সূচনা ডি? , যা ডিফল্ট কর্টরটিকে কল করে (অবিচ্ছিন্ন D::m)

ইটালিক মান এবং? অনিশ্চয়তা, দয়া করে এটি সংশোধন করতে সহায়তা করুন :-)

একটি C ++ 11 সংমিশ্রিত সংকলকটিতে জিনিসগুলি এমনভাবে কাজ করা উচিত:

??? (দয়া করে সাহায্য করুন যদি আমি এটি এখানে শুরু করি তবে যাইহোক এটি ভুল হয়ে যাবে)

একটি C ++ 14 সংমিশ্রিত সংকলকটিতে জিনিসগুলি এমনভাবে কাজ করা উচিত: ??? (দয়া করে সাহায্য করুন যদি আমি এটি এখানে শুরু করি তবে যাইহোক এটি ভুল হয়ে যাবে) (উত্তরের ভিত্তিতে খসড়া)

  • new A - ডিফল্ট-আরম্ভ A, সংকলক জেন কর্টর, (অস্বীকারহীনভাবে ছোঁয়া A::m) ( Aহ'ল পিওডি)

  • new A() - মান-ইনিশিয়ালাইজেশন A, যা [dcl.init] / 8 এর ২ পয়েন্টের পরে শূন্য-সূচনা হয়

  • new B - ডিফল্ট-আরম্ভ B, সংকলক জেন ctor, (leavs B::muninitialized) ( Bঅ POD হয়)

  • new B() - মান-প্রাথমিককরণ Bযা ডিফল্ট কর্টর ব্যবহারকারী-সংজ্ঞায়নের বিপরীতে সংকলক তৈরি হওয়ার কারণে সমস্ত ক্ষেত্র শূন্য-সূচনা করে।

  • new C - ডিফল্ট-আরম্ভ হয় C, যা ডিফল্ট কর্টর বলে। ( C::mশূন্য-ইনিশিয়েলড, Cনন-পিওডি)

  • new C() - মান-প্রাথমিককরণ C, যাকে ডিফল্ট কর্টর বলে। ( C::mশূন্য-সূচনা হয়)

  • new D - ডিফল্ট-সূচনা D( D::muninitialized হয়, Dঅ POD হয়)

  • new D() - মান-প্রাথমিককরণ D, যা ডিফল্ট কর্টরকে কল করে (অবিচ্ছিন্ন D::m)

  • new E - ডিফল্ট-আরম্ভ হয় E, যা কম্প কল। জেন ctor। ( E::mঅবিচ্ছিন্ন, ই নন-পিওডি)

  • new E() - মান-আরম্ভকরণ E, যা শূন্য-সূচনা করে E2 পয়েন্ট [dcl.init] / 8 ) থেকে

  • new F - ডিফল্ট-আরম্ভ হয় F, যা কম্প কল। জেন ctor। ( অবিচ্ছিন্ন F::m, Fপিওড-বিহীন)

  • new F() - মান- ইনিশিয়েলাইজF , যা ডিফল্ট-সূচনা হয় F ১ থেকে পয়েন্ট [dcl.init] / 8-তে ( Fযদি ব্যবহারকারী-ঘোষিত হয় এবং তার প্রথম ঘোষণায় স্পষ্টতই খেলাপি বা মুছে ফেলা না হয় তবে সিটি ফাংশনটি ব্যবহারকারী দ্বারা সরবরাহ করা হয় Link লিঙ্ক )


এখানে এটির একটি ভাল ব্যাখ্যা রয়েছে: en.cppreferences.com/w/cpp/language/default_constructor
রিচার্ড

4
আমি যতদূর বলতে পারি, এই উদাহরণগুলিতে কেবল সি ++ 98 এবং সি ++ 03 এর মধ্যে পার্থক্য রয়েছে। বিষয়টি এন 1161 (পরে সেই নথির পরে সংশোধন রয়েছে) এবং সিডব্লিউজি ডিআর # 178 তে বর্ণিত বলে মনে হচ্ছে । বাক্যে কথন নতুন বৈশিষ্ট্য ও POD একটি নতুন স্পেসিফিকেশন কারণে সি ++ 11 পরিবর্তন করা প্রয়োজন, এবং এটি সি ++ 11 শাব্দিক অপূর্ণতা কারণে সি ++ 14 মধ্যে আবার পরিবর্তিত হয়, কিন্তু এই ক্ষেত্রে প্রভাব না পরিবর্তিত হয় ।
ডায়প করুন

4
বিরক্তিকর সময়, struct D { D() {}; int m; };আপনার তালিকায় অন্তর্ভুক্ত মূল্যবান হতে পারে।
ইয়াক্ক - অ্যাডাম নেভ্রামামন্ট

উত্তর:


24

সি ++ 14 সি ++ 11- newএ [এক্সপ্লোরার নিউ] / 17 ([এক্সপ্রেস নতুন] / 15 এর সাথে তৈরি অবজেক্টের আরম্ভকরণ নির্দিষ্ট করে এবং নোটটি তখন নোট নয়, তবে মূল পাঠ্য ছিল):

একটি নতুন-এক্সপ্রেশন যা টাইপের একটি অবজেক্ট তৈরি করে Tসেই অবজেক্টটিকে নিম্নরূপিত করে:

  • যদি নতুন-ইনিশিয়ালাইজার বাদ দেওয়া হয় তবে অবজেক্টটি ডিফল্ট-ইনিশিয়ালাইজড (8.5)। [ দ্রষ্টব্য: যদি কোনও আরম্ভ করা হয় না, তবে অবজেক্টটির একটি অনির্দিষ্ট মান রয়েছে। - শেষ নোট ]
  • অন্যথায়, নতুন-ইনিশিয়ালাইজার সরাসরি-আরম্ভের জন্য 8.5 এর সূচনা বিধি অনুসারে ব্যাখ্যা করা হয়

ডিফল্ট-ইনিশিয়ালাইজেশন [dcl.init] / 7 (সি ++ 11 এ / 6 এ সংজ্ঞায়িত করা হয়, এবং শব্দটির নিজেই একই প্রভাব রয়েছে):

প্রকারের কোনও অবজেক্টের ডিফল্ট-আরম্ভ করার Tঅর্থ:

  • যদি T(সম্ভবত সিভি-যোগ্যতাসম্পন্ন) শ্রেণীর ধরণ (ক্লজ 9) হয় তবে এর জন্য ডিফল্ট কনস্ট্রাক্টর (12.1) Tবলা হয় (এবং আরম্ভটি যদি খারাপ থাকে তবেT ডিফল্ট কনস্ট্রাক্টর বা ওভারলোড রেজোলিউশন (13.3) ফলাফল না থাকলে ইনিশিয়েশনটি ) একটি ফাংশন যা মুছে ফেলা হয় বা প্রারম্ভিকতার প্রেক্ষাপট থেকে অ্যাক্সেসযোগ্য);
  • যদি Tএকটি অ্যারের ধরণ থাকে তবে প্রতিটি উপাদান ডিফল্ট-আরম্ভ হয় ;
  • অন্যথায়, কোনও আরম্ভ করা হয় না।

এইভাবে

  • new Aকেবলমাত্র Aডিফল্ট কনস্ট্রাক্টরকে ডেকে আনে, যা আরম্ভ হয় না m। নির্ধারিত মান। জন্য একই হতে হবে new B
  • new A() [dcl.init] / 11 (সি ++ 11 এ / 10) অনুসারে ব্যাখ্যা করা হয়েছে:

    এমন একটি বস্তুর যার প্রারম্ভিকর খালি সেট বন্ধনীগুলির সেট, অর্থাত্, ()মান-আরম্ভ হবে।

    এবং এখন [dcl.init] / 8 (সি ++ 11 / এ / 7) বিবেচনা করুন:

    টাইপের কোনও অবজেক্টের মূল্য-সূচনা করার Tঅর্থ:

    • যদি Tকোনও (সম্ভবত সিভি-যোগ্য) শ্রেণীর ধরণ (ক্লজ 9) হয় যার মধ্যে কোনও ডিফল্ট কনস্ট্রাক্টর (12.1) বা ব্যবহারকারী-প্রদত্ত বা মুছে ফেলা কোনও ডিফল্ট কনস্ট্রাক্টর থাকে তবে অবজেক্টটি ডিফল্ট-আরম্ভ হয়;
    • যদি Tকোনও ব্যবহারকারী প্রদত্ত বা মুছে ফেলা ডিফল্ট কনস্ট্রাক্টর ছাড়াই (সম্ভবত সিভি-কোয়ালিফাইড) শ্রেণীর ধরণ হয় তবে অবজেক্টটি শূন্য-আরম্ভ হয় এবং ডিফল্ট-আরম্ভের জন্য শব্দার্থ সীমাবদ্ধতাগুলি পরীক্ষা করা হয়, এবং যদি টিতে একটি তুচ্ছ ত্রুটিযুক্ত ডিফল্ট নির্মাণকারী থাকে, অবজেক্টটি ডিফল্ট-ইনিশিয়ালাইজড;
    • যদি Tএকটি অ্যারে টাইপ হয়, তবে প্রতিটি উপাদান মান-আরম্ভিত হয়;
    • অন্যথায়, অবজেক্টটি শূন্য-সূচনাযুক্ত ized

    সুতরাং new A()শূন্য-আরম্ভ হবে m। এবং এটি Aএবং এর সমতুল্য হওয়া উচিত B

  • new Cএবং new C()ডিফল্ট-আরম্ভ হবে বস্তুর আবার, যেহেতু গত উদ্ধৃতি থেকে প্রথম বুলেট পয়েন্ট প্রযোজ্য (গ ব্যবহারকারী-নির্ধারিত ডিফল্ট কনস্ট্রাকটর নেই তা!)। তবে, স্পষ্টতই, এখন mউভয় ক্ষেত্রেই নির্মাণকারীতে আরম্ভ করা হয়েছে।


† ভাল, এই অনুচ্ছেদে সি ++ 11 এ কিছুটা আলাদা শব্দ বলা আছে, যা ফলাফলকে পরিবর্তন করে না:

টাইপের কোনও অবজেক্টের মূল্য-সূচনা করার Tঅর্থ:

  • যদি Tকোনও ব্যবহারকারী-সরবরাহকারী কনস্ট্রাক্টর (12.1) সহ একটি (সম্ভবত সিভি-কোয়ালিফাইড) শ্রেণীর ধরণ (ক্লজ 9) হয় তবে এর জন্য ডিফল্ট কনস্ট্রাক্টর T বলা হয় (এবং টি এর অ্যাক্সেসযোগ্য ডিফল্ট কনস্ট্রাক্টর না থাকলে সূচনাটি খারাপ-গঠিত হয়);
  • যদি Tকোনও ব্যবহারকারী-সরবরাহকারী কনস্ট্রাক্টর ব্যতীত (সম্ভবত সিভি-কোয়ালিটিভড) নন-ইউনিয়ন শ্রেণীর ধরণ হয় তবে অবজেক্টটি শূন্য-ইনিশিয়েলাইজড এবং যদি Tস্পষ্টভাবে ঘোষিত ডিফল্ট কনস্ট্রাক্টর অ-তুচ্ছ হয় তবে তাকে কনস্ট্রাক্টর বলা হয়।
  • যদি Tএকটি অ্যারে টাইপ হয়, তবে প্রতিটি উপাদান মান-আরম্ভিত হয়;
  • অন্যথায়, অবজেক্টটি শূন্য-সূচনাযুক্ত ized

আহ তাই আপনি মূলত সি ++ ১৪ এর সাথে কথা বলছেন এবং সি ++ 11 এর জন্য উল্লেখগুলি বন্ধনীতে দেওয়া হয়েছে
গ্যাব্রিয়েল

@ গ্যাব্রিয়েল সঠিক আমি বলতে চাইছি, সি ++ 14 সর্বশেষতম মান, তাই এটি সামনে।
কলম্বো

4
স্ট্যান্ডার্ড জুড়ে প্রারম্ভিককরণের নিয়মগুলি আবিষ্কার করার চেষ্টা করার বিরক্তিকর বিষয়টি হ'ল ডিআরএসের মাধ্যমে প্রকাশিত সি ++ 14 এবং সি ++ 11 মানের মধ্যে প্রচুর পরিবর্তন (সবচেয়ে? সব?) হয়েছে এবং তাই ডি ফ্যাক্টো সি ++ 11 । এবং তারপরে পোস্ট-সি ++ ১৪ ডিআরএসও রয়েছে ...
টিসি

@ কলম্বো আমি এখনও বুঝতে পারছি না যে কেন struct A { int m; }; struct C { C() : m(){}; int m; };বিভিন্ন ফলাফল আসে এবং কী কারণে এ-তে এম প্রথম স্থানে শুরু হয়। আমি যে পরীক্ষাটি করেছিলাম তার জন্য আমি একটি উত্সর্গীকৃত থ্রেড খুলেছি এবং বিষয়টি স্পষ্ট করার জন্য আমি সেখানে আপনার ইনপুটটির প্রশংসা করব। ধন্যবাদ stackoverflow.com/questions/45290121/...
darkThoughts

12

নিম্নলিখিত উত্তরটি https://stackoverflow.com/a/620402/977038 উত্তরটি প্রসারিত করে যা C ++ 98 এবং C ++ 03 এর জন্য একটি রেফারেন্স হিসাবে কাজ করবে

উত্তরটি উদ্ধৃত করছি

  1. সি ++৯৯ এ দুটি ধরণের সূচনা হয়: শূন্য এবং ডিফল্ট
  2. সি ++ 2003 এ তৃতীয় প্রকারের সূচনা, মান আরম্ভকরণ যুক্ত করা হয়েছিল।

সি ++ 11 (n3242 এর প্রসঙ্গে)

আরম্ভকারীরা

৮.৫ ইনিশিয়ালাইজার [dcl.init] নির্দিষ্ট করে যে একটি পরিবর্তনশীল POD বা নন পিওডকে ব্রেস-আর-সম-ইনিশিয়ালাইজার হিসাবে আরম্ভ করা যেতে পারে যা হয় ব্রেসড-আর-তালিকা বা আরম্ভকারী-ধারাটি সামগ্রিকভাবে ব্রেস-বা-সমান- হিসাবে উল্লেখ করা যেতে পারে ইনিশিয়ালাইজার বা ব্যবহার (এক্সপ্রেশন-তালিকা) । সি ++ ১১ এর পূর্বে, কেবল (এক্সপ্রেশন-তালিকা) বা ইনিশিয়ালাইজার-ক্লজটি সমর্থিত ছিল যদিও ইনিশিয়ালার-ক্লজটি আরও সীমাবদ্ধ ছিল তবে আমাদের সি ++ 11 এ যা আছে। সি ++ 11 এ, ইনিশিয়ালার-ক্লজ এখন অ্যাসাইনমেন্ট-এক্সপ্রেশন বাদে ব্রেসড-আরআই-তালিকা সমর্থন করেযেমনটি সি ++ 03 তে ছিল। নিম্নলিখিত ব্যাকরণটি নতুন সমর্থিত ধারাটির সংক্ষিপ্তসার করেছে, যেখানে অংশটি গা bold়ভাবে সি ++ 11 স্ট্যান্ডার্ডে নতুনভাবে যুক্ত করা হয়েছে।

ইনিশিয়ালাইজার:
    ব্রেস-বা-সম-ইনিশিয়ালাইজার
    (এক্সপ্রেশন-লিস্ট)
ব্রেস-বা-সম-ইনিশিয়ালাইজার:
    = ইনিশিয়ালার-ক্লজ
    ব্রেসড-আরআই-লিস্ট
ইনিশিয়ালাইজার-ক্লজ:
    অ্যাসাইনমেন্ট-এক্সপ্রেশন
    ব্রাসেড-আরিন-লিস্ট
ইনিশিয়ালাইজার-লিস্ট:
    ইনিশিয়ালার-ক্লজ ... অপ্ট
    ইনিশিয়ালাইজার-তালিকা, ইনিশিয়ালাইজার-ক্লজ ... অপ্ট **
ব্রেসড-আরআইডি-তালিকা:
    {আরম্ভকারী-তালিকা, অপ্ট}
    {}

আরম্ভ

সি ++ 03 এর মতো সি ++ 11 এখনও তিনটি প্রারম্ভিক সমর্থন করে


বিঃদ্রঃ

গা bold়ভাবে হাইলাইট করা অংশটি সি ++ 11 এ যুক্ত করা হয়েছে এবং যেটি বের করা হয়েছে তা সি ++ 11 থেকে সরানো হয়েছে।

  1. ইনিশিয়ালাইজারের ধরণ: 8.5.5 [dcl.init] _ জেরো-ইনিশিয়ালাইজ_

নিম্নলিখিত ক্ষেত্রে সম্পাদিত

  • স্ট্যাটিক বা থ্রেড স্টোরেজ সময়কাল সহ অবজেক্টগুলি শূন্য-আরম্ভ হয় ized
  • অ্যারে উপাদানগুলির তুলনায় যদি কম ইনিশিয়ালাইজার থাকে, তবে প্রতিটি উপাদান সুস্পষ্টভাবে আরম্ভ করা হবে না শূন্য-আরম্ভ হবে
  • মান-আরম্ভের সময় , যদি টি কোনও ব্যবহারকারী-সরবরাহকারীর নির্মাণ ব্যতীত একটি (সম্ভবত সিভি-কোয়ালিটিভড) নন-ইউনিয়ন শ্রেণির ধরণ হয় তবে অবজেক্টটি শূন্য-আরম্ভ হয়।

টির শর্টের অর্থ বা রেফারেন্সের শূন্য-সূচনা করার জন্য:

  • যদি টি একটি স্কেলার প্রকার (3.9) হয় তবে অবজেক্টটি মান 0 (শূন্য) এ সেট হয়, এটি অবিচ্ছেদ্য ধ্রুবক অভিব্যক্তি হিসাবে নেওয়া হয় , টিতে রূপান্তরিত হয়;
  • যদি টি হ'ল (সম্ভবত সিভি-কোয়ালিফাইড) নন-ইউনিয়ন শ্রেণীর ধরণ, প্রতিটি অ-স্থিতিশীল ডেটা সদস্য এবং প্রতিটি বেস-ক্লাস সাবোবজেক্ট শূন্য-ইনিশিয়েটেড হয় এবং প্যাডিং শূন্য বিটগুলিতে আরম্ভ করা হয়;
  • যদি টি হ'ল (সম্ভবত সিভি-কোয়ালিফাইড) ইউনিয়ন প্রকার, অবজেক্টের প্রথম অ স্থিত নামযুক্ত ডেটা সদস্য শূন্য আরম্ভ এবং প্যাডিং শূন্য বিটগুলিতে আরম্ভ করা হয়;
  • যদি টি অ্যারের ধরণ হয় তবে প্রতিটি উপাদান শূন্য-সূচনাযুক্ত হয়;
  • যদি টি একটি রেফারেন্স টাইপ হয় তবে কোনও সূচনা হয় না।

2. প্রারম্ভকালীন প্রকার: 8.5.6 [dcl.init] _ পূর্বনির্ধারিত-আরম্ভকরণ_

নিম্নলিখিত ক্ষেত্রে সম্পাদিত

  • যদি নতুন-ইনিশিয়ালઝર বাদ দেওয়া হয় তবে অবজেক্টটি ডিফল্ট-ইনিশিয়ালাইজড হয়; যদি কোনও সূচনা সম্পন্ন না হয় তবে অবজেক্টটির অনির্দিষ্ট মান রয়েছে।
  • যদি কোনও বস্তুর জন্য কোনও আরম্ভকারী নির্দিষ্ট না করা থাকে তবে স্থিতিশীল বা থ্রেড স্টোরেজ সময়কাল সহ অবজেক্টগুলি বাদ দিয়ে অবজেক্টটি ডিফল্ট-আরম্ভ করা হয়
  • যখন কোনও বেস বর্গ বা কোনও স্থিতিশীল ডেটা সদস্যের কনস্ট্রাক্টর ইনিশিয়ালাইজার তালিকায় উল্লেখ না করা হয় এবং সেই কনস্ট্রাক্টর বলা হয়।

টি টাইপের কোনও অবজেক্টের ডিফল্ট-আরম্ভ করার জন্য:

  • যদি টি হ'ল (সম্ভবত সিভি-কোয়ালিফাইড) নন-পিওডি ক্লাস টাইপ (ক্লজ 9), টির জন্য ডিফল্ট কনস্ট্রাক্টর বলা হয় (এবং টি যদি অ্যাক্সেসযোগ্য ডিফল্ট কনস্ট্রাক্টর না থাকে তবে আরম্ভকরণটি অসুস্থ হয়);
  • যদি টি অ্যারের ধরণ হয় তবে প্রতিটি উপাদান ডিফল্ট-আরম্ভ হয়;
  • অন্যথায়, কোনও আরম্ভ করা হয় না।

দ্রষ্টব্য সি ++ 11 অবধি, কোনও আরম্ভকারী ব্যবহার করা না হলে কেবল স্বয়ংক্রিয় স্টোরেজ সময়কাল সহ নন-পিওড শ্রেণীর ধরণগুলি ডিফল্ট-আরম্ভিত হিসাবে বিবেচিত হবে।


3. প্রারম্ভক প্রকার: 8.5.7 [dcl.init] _ মূল্য-ইনিশিয়ালাইজ_

  1. যখন কোনও অবজেক্ট (নামহীন অস্থায়ী, নামযুক্ত ভেরিয়েবল, ডায়নামিক স্টোরেজ সময়কাল বা নন-স্ট্যাটিক ডেটা মেম্বার) যার প্রাথমিককরণ খালি সেট বন্ধনীর সেট, অর্থাৎ, () বা ধনুর্বন্ধনী {}

টাইপ টির একটি অবজেক্টের মূল্য-সূচনা করার জন্য:

  • যদি টি ব্যবহারকারীর দ্বারা সরবরাহিত কনস্ট্রাক্টর (12.1) সহ একটি (সম্ভবত সিভি-যোগ্য) শ্রেণীর ধরণ (ক্লজ 9) হয় তবে টি এর জন্য ডিফল্ট কনস্ট্রাক্টর বলা হয় (এবং টি যদি অ্যাক্সেসযোগ্য ডিফল্ট কনস্ট্রাক্টর না থাকে তবে আরম্ভকরণটি অসুস্থ হয়) ;
  • যদি টি কোনও (প্রদত্ত সিভি-কোয়ালিফাইড) নন-ইউনিয়ন শ্রেণীর প্রকার, কোনও ব্যবহারকারী-সরবরাহকারী নির্মাতারা ব্যতীত, তবে প্রতিটি অ-স্থিতিশীল ডেটা সদস্য এবং টি-এর বেস-ক্লাস উপাদানটি মান-আরম্ভ হয়; তারপরে অবজেক্টটি শূন্য-ইনিশিয়ালাইজড এবং যদি টি এর স্পষ্টভাবে ঘোষিত ডিফল্ট কনস্ট্রাক্টর অ-তুচ্ছ হয় তবে তাকে কনস্ট্রাক্টর বলা হয়।
  • যদি টি অ্যারের ধরণ হয় তবে প্রতিটি উপাদান মান-আরম্ভ হয়;
  • অন্যথায়, অবজেক্টটি শূন্য-সূচনাযুক্ত ized

তাই সংক্ষেপে

উল্লেখ্য মান থেকে প্রাসঙ্গিক উদ্ধৃতি হাইলাইট হয় সাহসী

  • নতুন এ: ডিফল্ট-ইনিশিয়ালাইজগুলি (এ :: মি অবিশ্বাস্য পাতা ছেড়ে দেয়)
  • নতুন এ (): মান শুরুর প্রার্থীর কোনও ব্যবহারকারীর সরবরাহ করা বা মোছা ডিফল্ট কনস্ট্রাক্টর না থাকায় শূন্য-ইনিশিয়ালাইজ এ। যদি টি কোনও ব্যবহারকারীর সরবরাহকৃত কনস্ট্রাক্টর ছাড়াই (সম্ভবত সিভি-কোয়ালিটিভড) নন-ইউনিয়ন শ্রেণীর ধরণ হয় তবে অবজেক্টটি শূন্য-ইনিশিয়েলড এবং যদি টি-র স্পষ্টভাবে ঘোষিত ডিফল্ট কনস্ট্রাক্টর অ-তুচ্ছ হয় তবে তাকে কনস্ট্রাক্টর বলা হয়।
  • নতুন বি: ডিফল্ট-ইনিশিয়ালাইজগুলি (বি :: মি অবিশ্বাস্য প্রস্থান করে)
  • নতুন বি (): মান-বি সূচনা করে যা সমস্ত ক্ষেত্র শূন্য-সূচনা করে; যদি টি ব্যবহারকারীর দ্বারা সরবরাহিত কনস্ট্রাক্টর (12.1) সহ একটি (সম্ভবত সিভি-যোগ্যতাসম্পন্ন) শ্রেণীর ধরণ (ক্লজ 9) হয় তবে টি এর জন্য ডিফল্ট কনস্ট্রাক্টর বলা হয়
  • নতুন সি: ডিফল্ট-প্রাথমিককরণ সি, যাকে ডিফল্ট কর্টর বলে। যদি টি হ'ল (সম্ভবত সিভি-কোয়ালিটিভড) শ্রেণীর ধরণ (ক্লজ 9), টি-র জন্য ডিফল্ট কনস্ট্রাক্টর বলা হয় , তাছাড়া নতুন-ইনিশিয়ালার বাদ দেওয়া হলে অবজেক্টটি ডিফল্ট-আরম্ভ হয়
  • নতুন সি (): মান-আরম্ভ করে সি, যা ডিফল্ট কর্টরকে ডাকে। যদি টি ব্যবহারকারীর দ্বারা সরবরাহিত কনস্ট্রাক্টর (12.1) সহ একটি (সম্ভবত সিভি-যোগ্য) শ্রেণীর ধরণ (ক্লজ 9) হয় তবে টি এর জন্য ডিফল্ট কনস্ট্রাক্টর বলা হয়। তদুপরি, যে বস্তুর প্রারম্ভক খালি সেট বন্ধনীর সেট, অর্থাৎ, (), সেটির মান-আরম্ভ হবে

0

আমি নিশ্চিত করতে পারি যে সি ++ 11-এ, সি ++ 14 এর অধীনে প্রশ্নে উল্লিখিত সমস্ত কিছুই কমপক্ষে সংকলক বাস্তবায়ন অনুসারে সঠিক।

এটি যাচাই করার জন্য, আমি আমার টেস্ট স্যুটে নিম্নলিখিত কোডটি যুক্ত করেছি । আমি -std=c++11 -O3জিসিসি 7.4.0, জিসিসি 5.4.0, কলং 10.0.1, এবং ভিএস 2017 এবং পরীক্ষার পাশের নীচে সমস্ত পরীক্ষা করেছি।

#include <gtest/gtest.h>
#include <memory>

struct A { int m;                    };
struct B { int m;            ~B(){}; };
struct C { int m; C():m(){}; ~C(){}; };
struct D { int m; D(){};             };
struct E { int m; E() = default;     };
struct F { int m; F();               }; F::F() = default;

// We use this macro to fill stack memory with something else than 0.
// Subsequent calls to EXPECT_NE(a.m, 0) are undefined behavior in theory, but
// pass in practice, and help illustrate that `a.m` is indeed not initialized
// to zero. Note that we initially tried the more aggressive test
// EXPECT_EQ(a.m, 42), but it didn't pass on all compilers (a.m wasn't equal to
// 42, but was still equal to some garbage value, not zero).
//
#define FILL { int m = 42; EXPECT_EQ(m, 42); }

// We use this macro to fill heap memory with something else than 0, before
// doing a placement new at that same exact location. Subsequent calls to
// EXPECT_EQ(a->m, 42) are undefined behavior in theory, but pass in practice,
// and help illustrate that `a->m` is indeed not initialized to zero.
//
#define FILLH(b) std::unique_ptr<int> bp(new int(42)); int* b = bp.get(); EXPECT_EQ(*b, 42)

TEST(TestZero, StackDefaultInitialization)
{
    { FILL; A a; EXPECT_NE(a.m, 0); } // UB!
    { FILL; B a; EXPECT_NE(a.m, 0); } // UB!
    { FILL; C a; EXPECT_EQ(a.m, 0); }
    { FILL; D a; EXPECT_NE(a.m, 0); } // UB!
    { FILL; E a; EXPECT_NE(a.m, 0); } // UB!
    { FILL; F a; EXPECT_NE(a.m, 0); } // UB!
}

TEST(TestZero, StackValueInitialization)
{
    { FILL; A a = A(); EXPECT_EQ(a.m, 0); }
    { FILL; B a = B(); EXPECT_EQ(a.m, 0); }
    { FILL; C a = C(); EXPECT_EQ(a.m, 0); }
    { FILL; D a = D(); EXPECT_NE(a.m, 0); } // UB!
    { FILL; E a = E(); EXPECT_EQ(a.m, 0); }
    { FILL; F a = F(); EXPECT_NE(a.m, 0); } // UB!
}

TEST(TestZero, StackListInitialization)
{
    { FILL; A a{}; EXPECT_EQ(a.m, 0); }
    { FILL; B a{}; EXPECT_EQ(a.m, 0); }
    { FILL; C a{}; EXPECT_EQ(a.m, 0); }
    { FILL; D a{}; EXPECT_NE(a.m, 0); } // UB!
    { FILL; E a{}; EXPECT_EQ(a.m, 0); }
    { FILL; F a{}; EXPECT_NE(a.m, 0); } // UB!
}

TEST(TestZero, HeapDefaultInitialization)
{
    { FILLH(b); A* a = new (b) A; EXPECT_EQ(a->m, 42); } // ~UB
    { FILLH(b); B* a = new (b) B; EXPECT_EQ(a->m, 42); } // ~UB
    { FILLH(b); C* a = new (b) C; EXPECT_EQ(a->m, 0);  }
    { FILLH(b); D* a = new (b) D; EXPECT_EQ(a->m, 42); } // ~UB
    { FILLH(b); E* a = new (b) E; EXPECT_EQ(a->m, 42); } // ~UB
    { FILLH(b); F* a = new (b) F; EXPECT_EQ(a->m, 42); } // ~UB
}

TEST(TestZero, HeapValueInitialization)
{
    { FILLH(b); A* a = new (b) A(); EXPECT_EQ(a->m, 0);  }
    { FILLH(b); B* a = new (b) B(); EXPECT_EQ(a->m, 0);  }
    { FILLH(b); C* a = new (b) C(); EXPECT_EQ(a->m, 0);  }
    { FILLH(b); D* a = new (b) D(); EXPECT_EQ(a->m, 42); } // ~UB
    { FILLH(b); E* a = new (b) E(); EXPECT_EQ(a->m, 0);  }
    { FILLH(b); F* a = new (b) F(); EXPECT_EQ(a->m, 42); } // ~UB
}

TEST(TestZero, HeapListInitialization)
{
    { FILLH(b); A* a = new (b) A{}; EXPECT_EQ(a->m, 0);  }
    { FILLH(b); B* a = new (b) B{}; EXPECT_EQ(a->m, 0);  }
    { FILLH(b); C* a = new (b) C{}; EXPECT_EQ(a->m, 0);  }
    { FILLH(b); D* a = new (b) D{}; EXPECT_EQ(a->m, 42); } // ~UB
    { FILLH(b); E* a = new (b) E{}; EXPECT_EQ(a->m, 0);  }
    { FILLH(b); F* a = new (b) F{}; EXPECT_EQ(a->m, 42); } // ~UB
}

int main(int argc, char **argv)
{
    ::testing::InitGoogleTest(&argc, argv);
    return RUN_ALL_TESTS();
}

যে জায়গাগুলির UB!উল্লেখ করা হয়েছে সেগুলি অপরিজ্ঞাত আচরণ, এবং আসল আচরণগুলি অনেকগুলি কারণের উপর নির্ভর করে ( a.mসম্ভবত 42, 0 বা অন্য কোনও আবর্জনার সমান হতে পারে)। যে জায়গাগুলির ~UBউল্লেখ করা হয়েছে সেগুলি তত্ত্বের ক্ষেত্রেও অপরিজ্ঞাত আচরণ, তবে বাস্তবে নতুন একটি প্লেসমেন্ট ব্যবহারের কারণে এটি a->m42 এর চেয়ে অন্য যে কোনও কিছুর সমান হবে না বলে খুব সম্ভবত সম্ভাবনা রয়েছে ।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.