সদস্য কনস্ট্রাক্টর এবং ডেস্ট্রাক্টর কলের অর্ডার


120

ওহ সি ++ গুরু, আমি আপনার প্রজ্ঞার সন্ধান করি। আমার সাথে স্ট্যান্ডার্ডিজ বলুন এবং সি ++ নীচের প্রোগ্রামটির নিশ্চয়তা দিলে আমার বলুন:

#include <iostream>
using namespace std;

struct A
{
    A() { cout << "A::A" << endl; }
    ~A() { cout << "A::~" << endl; }
};

struct B
{
    B() { cout << "B::B" << endl; }
    ~B() { cout << "B::~" << endl; }
};

struct C
{
    C() { cout << "C::C" << endl; }
    ~C() { cout << "C::~" << endl; }
};

struct Aggregate
{
    A a;
    B b;
    C c;
};

int main()
{
    Aggregate a;
    return 0;
}

সর্বদা উত্পাদন করা হবে

A::A
B::B
C::C
C::~
B::~
A::~

অন্য কথায়, সদস্যগণ কি ঘোষণার আদেশ দ্বারা আরম্ভ করা এবং বিপরীত ক্রমে নষ্ট করা গ্যারান্টিযুক্ত?


8
ক্লাসগুলি বড় এবং অস্বাস্থ্যকর হয়ে উঠলে এটি সূক্ষ্ম বাগের যুক্তিসঙ্গত সাধারণ কারণ। যখন আপনার কাছে 50 জন ডেটা সদস্য রয়েছে এবং তাদের মধ্যে অনেকগুলি কন্সট্রাক্টর ইনটালাইজার তালিকায় প্রাথমিকভাবে শুরু করা হয় তখন সহজেই নির্ধারণ করা যেতে পারে যে ক্রমটি ক্রমটি প্রাথমিকের তালিকার ক্রম। সর্বোপরি কোড লেখকরা সাবধানতার সাথে তালিকার আদেশ দিয়েছেন ... তাই না?
পারমাকিউড

উত্তর:


138

অন্য কথায়, সদস্যগণ কি ঘোষণার আদেশ দ্বারা আরম্ভ করা এবং বিপরীত ক্রমে নষ্ট করা গ্যারান্টিযুক্ত?

হ্যাঁ 12.6.2 দেখুন

6 সূচনা নিম্নলিখিত ক্রমে এগিয়ে হইবে:

  • প্রথমে এবং কেবল নীচে বর্ণিত সর্বাধিক উত্সযুক্ত শ্রেণীর নির্মাণকারীর জন্য, ভার্চুয়াল বেস শ্রেণিগুলি বেস শ্রেণীর নির্দেশিত অ্যাসাইক্লিক গ্রাফের গভীরতা-প্রথম বাম থেকে ডান দিকের ট্র্যাভার্সাল অনুসারে প্রদর্শিত ক্রম হিসাবে সূচনা করা হবে, যেখানে "বাম -থেকে-ডান "হল উত্পন্ন শ্রেণীর বেস-সুনির্দিষ্ট-তালিকার বেস শ্রেণীর নামগুলি উপস্থিত করার ক্রম।

  • তারপরে, বেস-স্পেসিফায়ার-তালিকায় (মেমো-ইনিশিয়ালাইজের ক্রম নির্বিশেষে) সরাসরি বেস ক্লাসগুলি ঘোষণা আদেশে সূচনা করা হবে।

  • তারপরে, অ স্থির ডেটা সদস্যদের শ্রেণি সংজ্ঞায় ঘোষিত ক্রমে (আবার স্মৃতি-আরম্ভকারীদের আদেশ নির্বিশেষে) শুরু করা হবে।

  • অবশেষে, কনস্ট্রাক্টর বডির যৌগিক বিবৃতি কার্যকর করা হয়। [দ্রষ্টব্য: ঘোষণার আদেশটি বেস এবং সদস্য সাবোবজেক্টগুলি আরম্ভের বিপরীত ক্রমে নষ্ট হয়ে গেছে তা নিশ্চিত করার জন্য বাধ্যতামূলক। অন্তর্ভুক্ত নোট]


2
যদি আমি সঠিকভাবে মনে রাখি তবে হ্যাঁ উভয়ের ... এটিকে একটি স্ট্যাক হিসাবে মনে করুন। প্রথম ধাক্কা, শেষ পপ করা। সুতরাং, আপনার প্রথম উদাহরণটি ইনস্ট্যান্ট করার সময়, এটি স্ট্যাকের ক্রম অনুসারে মেমোরিতে স্থানান্তরিত করা হয়। তারপরে, দ্বিতীয়টি ধাক্কা দেওয়া হয়, তৃতীয়টি দ্বিতীয়টির চেয়ে বেশি এবং আরও এগিয়ে। তারপরে, আপনার দৃষ্টান্তগুলি ধ্বংস করার পরে, প্রোগ্রামটি সর্বপ্রথম ধ্বংসকারীটির সন্ধান করবে, শেষটি যেটিকে ধাক্কা দেওয়া হয়েছে। তবে আমি এটি এভাবে ব্যাখ্যা করতে ভুল হতে পারি, তবে সি / সি ++ এবং এএসএম করার সময় এটিই আমি শিখেছি।
উইল মারকুইলার

29

হ্যাঁ, তারা (অ স্থির সদস্য যে হয়)। প্রারম্ভিককরণ (নির্মাণ) এর জন্য 12.6.2 / 5 এবং ধ্বংসের জন্য 12.4 / 6 দেখুন।


10

হ্যাঁ, স্ট্যান্ডার্ড গ্যারান্টি দেয় যে বস্তুগুলি তাদের তৈরি করা বিপরীত ক্রমে ধ্বংস হয়ে যায়। কারণটি হ'ল এক বস্তু অন্যটি ব্যবহার করতে পারে, সুতরাং এটির উপর নির্ভর করে। বিবেচনা:

struct A { };

struct B {
 A &a;
 B(A& a) : a(a) { }
};

int main() {
    A a;
    B b(a);
}

এর aআগে যদি ধ্বংস করা হয় bতবে bঅবৈধ সদস্যের রেফারেন্স রাখে। বিপরীত ক্রমে বস্তুগুলি তৈরি করা হয়েছিল যাতে সেগুলি তৈরি হয়েছিল আমরা সঠিক ধ্বংসের গ্যারান্টি দিয়েছি।


আমি আসলে কখনই বিবেচনা করি নি যে এই বিধি স্কোপ সদস্যদের ধ্বংস আদেশের ক্ষেত্রেও প্রযোজ্য!
ইয়ানো

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