অনুলিপি এলিজেন বিভিন্ন পরিস্থিতিতে ঘটতে অনুমতি দেওয়া হয়েছিল। যাইহোক, এটি অনুমোদিত হলেও, কোডটি এখনও কাজ করতে সক্ষম হয়েছিল যেন অনুলিপিটি অনুপযুক্ত ছিল না। যথা, সেখানে একটি অ্যাক্সেসযোগ্য অনুলিপি এবং / অথবা মুভ কনস্ট্রাক্টর থাকতে হয়েছিল।
গ্যারান্টিযুক্ত কপি বিলোপ সি ++ ধারণা, এই ধরনের যে কিছু বিশেষ পরিস্থিতির যেখানে কপি / প্যাচসমূহ লুপ্ত হতে পারে আসলে একটি কপি / পদক্ষেপ ঘটান না একটি নম্বর redefines এ সব । সংকলক একটি অনুলিপি গোপন করছে না; মানটি বলে যে এরকম কোনও অনুলিপি কখনও ঘটতে পারে নি।
এই ফাংশনটি বিবেচনা করুন:
T Func() {return T();}
অন-গ্যারান্টিযুক্ত অনুলিপি এলিজেন নিয়মের অধীনে, এটি একটি অস্থায়ী তৈরি করবে, তারপরে সেই অস্থায়ী থেকে ফাংশনের রিটার্ন মানটিতে চলে যাবে। এই মুভ অপারেশনটি এলিডযুক্ত হতে পারে T
তবে এটি কখনও ব্যবহার না করা সত্ত্বেও একটি অ্যাক্সেসযোগ্য মুভ কনস্ট্রাক্টর থাকতে হবে।
একইভাবে:
T t = Func();
এটি হ'ল অনুলিপি t
। এটির t
রিটার্ন মান সহ আরম্ভের অনুলিপি করা হবে Func
। যাইহোক, T
এখনও একটি মুভি কনস্ট্রাক্টর থাকতে হবে, যদিও এটি বলা হবে না।
গ্যারান্টিযুক্ত অনুলিপি এলিজিয়াল একটি মূল মূল্য প্রকাশের অর্থ পুনরায় সংজ্ঞা দেয় । প্রাক-সি ++ 17, মূল্যগুলি অস্থায়ী বস্তু। সি ++ ১ In-এ, একটি প্রাথমিক ধারণাটি কেবল এমন কিছু যা সাময়িকভাবে রূপায়িত করতে পারে তবে এটি এখনও অস্থায়ী নয়।
আপনি যদি প্রলিউয়ের ধরণের কোনও অবজেক্টটি আরম্ভ করার জন্য কোনও মূল্য ব্যবহার করেন, তবে কোনও অস্থায়ী বস্তুগত হয় না। আপনি যখন করেন return T();
, এটি কোনও পূর্বমূল্যের মাধ্যমে ফাংশনের রিটার্ন মানকে আরম্ভ করে। যেহেতু ফাংশনটি ফিরে আসে T
, তাই কোনও অস্থায়ী তৈরি হয় না; মূল্যের সূচনাটি প্রত্যক্ষভাবে প্রত্যক্ষ মানের সূচনা করে।
বোঝার বিষয়টি হ'ল, যেহেতু রিটার্ন মান একটি পূর্বমূল্য, এটি এখনও কোনও বস্তু নয় । এটি কেবল কোনও জিনিসের জন্য কেবল একটি সূচনাযাত্রা T()
।
আপনি যখন করেন T t = Func();
, প্রত্যাবর্তনের মূল্যের মূল্য সরাসরি অবজেক্টটিকে আরম্ভ করে t
; কোনও "অস্থায়ী এবং অনুলিপি / সরানো" পর্যায়ে নেই। যেহেতু Func()
এর রিটার্ন মান হ'ল একটি মূল্যমানের সমতুল্য T()
, t
সরাসরি দ্বারা শুরু করা হয় T()
ঠিক যেমনটি আপনি করেছেন T t = T()
।
যদি কোনও মূল্য অন্য কোনও উপায়ে ব্যবহার করা হয়, তবে মূল্যটি একটি অস্থায়ী বস্তুকে রূপায়িত করবে, যা সেই অভিব্যক্তিতে ব্যবহৃত হবে (বা কোনও অভিব্যক্তি না থাকলে ফেলে দেওয়া হবে)। সুতরাং আপনি যদি তা করেন const T &rt = Func();
, তবে প্রাথমিক অস্থায়ী আজীবন এক্সটেনশনের স্টাফ সহ T()
, যার উল্লেখটি অস্থায়ী (আরম্ভকারী হিসাবে ব্যবহার করে ) কার্যকর করা হবে rt
।
গ্যারান্টিযুক্ত এলিজেন্স আপনাকে অনুমতি দেয় এমন একটি জিনিস হ'ল অচল জিনিস যা ফেরত দেওয়া হয়। উদাহরণস্বরূপ, lock_guard
অনুলিপি করা বা সরানো যায় না, সুতরাং আপনার কোনও ফাংশন থাকতে পারে না যা এটি মূল্য দিয়ে ফিরিয়ে দেয়। তবে গ্যারান্টিযুক্ত অনুলিপি সহ, আপনি পারেন।
গ্যারান্টেড এলিজেন্স সরাসরি সূচনাতেও কাজ করে:
new T(FactoryFunction());
যদি মান অনুসারে FactoryFunction
রিটার্ন দেয় তবে T
এই অভিব্যক্তিটি বরাদ্দ মেমরিতে রিটার্নের মানটি অনুলিপি করবে না। এটি পরিবর্তে মেমরি বরাদ্দ করবে এবং বরাদ্দ মেমরিটি সরাসরি ফাংশন কলের জন্য রিটার্ন মান মেমরি হিসাবে ব্যবহার করবে ।
সুতরাং ফ্যাক্টরি ফাংশনগুলি যা মান অনুসারে প্রত্যাবর্তন করে সেগুলি এমনকি অজানা মেমরির সম্পর্কে সরাসরি না জেনে শুরু করতে পারে। এতক্ষণ এই ফাংশনগুলি অভ্যন্তরীণভাবে অবশ্যই গ্যারান্টিযুক্ত অনুলিপি নিয়মের অনুসরণ করে follow তাদের টাইপের একটি মূল্য ফেরত দিতে হবে T
।
অবশ্যই এটি কাজ করে:
new auto(FactoryFunction());
আপনি টাইপনেম লিখতে পছন্দ করেন না ক্ষেত্রে।
এটি সনাক্ত করা গুরুত্বপূর্ণ যে উপরের গ্যারান্টিগুলি কেবল মূল্যগুলির জন্য কাজ করে। এটি হল, নামযুক্ত ভেরিয়েবলটি ফেরত দেওয়ার সময় আপনি কোনও গ্যারান্টি পাবেন না :
T Func()
{
T t = ...;
...
return t;
}
এই উদাহরণস্বরূপ, t
এখনও একটি অ্যাক্সেসযোগ্য অনুলিপি / সরানো কনস্ট্রাক্টর থাকতে হবে। হ্যাঁ, সংকলক অনুলিপি / সরানো অপ্টিমাইজ করতে বেছে নিতে পারেন। তবে সংকলকটিকে এখনও একটি অ্যাক্সেসযোগ্য অনুলিপি / সরানো কনস্ট্রাক্টরের অস্তিত্ব যাচাই করতে হবে।
সুতরাং নামমাত্র রিটার্ন মান অপ্টিমাইজেশনের (এনআরভিও) কোনও পরিবর্তন হয় না।