এটি কেন ভাল প্যাটার্ন তা বোঝার জন্য আমাদের সি ++ 03 এবং সি ++ 11 এ দুটি বিকল্পই পরীক্ষা করা উচিত।
আমাদের কাছে C ++ 03 পদ্ধতি রয়েছে std::string const&
:
struct S
{
std::string data;
S(std::string const& str) : data(str)
{}
};
এই ক্ষেত্রে, সর্বদা একটি একক অনুলিপি সম্পাদিত হবে। যদি আপনি কোনও কাঁচা সি স্ট্রিং থেকে নির্মাণ করেন তবে একটি নির্মিত std::string
হবে, তারপরে আবার অনুলিপি করুন: দুটি বরাদ্দ।
এখানে একটি রেফারেন্স নেওয়ার সি ++ 03 পদ্ধতি রয়েছে std::string
, তারপরে এটিকে লোকালটিতে অদলবদল করুন std::string
:
struct S
{
std::string data;
S(std::string& str)
{
std::swap(data, str);
}
};
এটি "মুভ সেমেন্টিকস" এর C ++ 03 সংস্করণ, এবং swap
প্রায়শই এটি করার জন্য খুব সস্তা হতে অনুকূলিত করা যেতে পারে (অনেকটা এর মতো move
)। এটি প্রসঙ্গে বিশ্লেষণ করা উচিত:
S tmp("foo");
std::string s("foo");
S tmp2(s);
এবং আপনাকে অস্থায়ী হিসাবে গঠনের জন্য জোর করে std::string
, তারপরে এটি বাতিল করুন। (একটি অস্থায়ী std::string
অ-কনস্ট্যান্ট রেফারেন্সকে আবদ্ধ করতে পারে না)। তবে শুধুমাত্র একটি বরাদ্দ করা হয়। সি ++ 11 সংস্করণটি গ্রহণ করবে &&
এবং আপনাকে এটির সাথে std::move
বা একটি অস্থায়ী সহ কল করতে হবে : এর জন্য কলারটি স্পষ্টভাবে কলের বাইরে একটি অনুলিপি তৈরি করে এবং সেই অনুলিপিটি ফাংশন বা কনস্ট্রাক্টারে স্থানান্তরিত করে।
struct S
{
std::string data;
S(std::string&& str): data(std::move(str))
{}
};
ব্যবহার:
S tmp("foo");
std::string s("foo");
S tmp2(std::move(s));
এরপরে, আমরা সম্পূর্ণ সি ++ 11 সংস্করণটি করতে পারি, যা অনুলিপি এবং উভয়কেই সমর্থন করে move
:
struct S
{
std::string data;
S(std::string const& str) : data(str) {}
S(std::string && str) : data(std::move(str)) {}
};
এরপরে আমরা এটি কীভাবে ব্যবহৃত হয় তা পরীক্ষা করতে পারি:
S tmp( "foo" );
std::string bar("bar");
S tmp2( bar );
std::string bar2("bar2");
S tmp3( std::move(bar2) );
এটি বেশ পরিষ্কার যে এই 2 ওভারলোড কৌশলটি উপরের দুটি সি ++ 03 শৈলীর চেয়ে কম না হলেও কম দক্ষ efficient আমি এই 2-ওভারলোড সংস্করণটিকে "সর্বাধিক অনুকূল" সংস্করণটি ডাব করব।
এখন, আমরা কপিরাইট-এর অনুলিপি পরীক্ষা করব:
struct S2 {
std::string data;
S2( std::string arg ):data(std::move(x)) {}
};
এই পরিস্থিতিতে প্রতিটি পরিস্থিতিতে:
S2 tmp( "foo" );
std::string bar("bar");
S2 tmp2( bar );
std::string bar2("bar2");
S2 tmp3( std::move(bar2) );
আপনি যদি এই সর্বাধিক অনুকূল "সংস্করণ" এর সাথে তুলনা করেন, আমরা ঠিক আরও একটি অতিরিক্ত করবো move
! একবারে আমরা অতিরিক্ত কিছু করি না copy
।
সুতরাং আমরা যদি ধরে নিই যে move
এটি সস্তা, এই সংস্করণটি আমাদের সর্বাধিক অনুকূল সংস্করণ হিসাবে প্রায় একই পারফরম্যান্স পেয়েছে, তবে 2 গুণ কম কোড।
এবং যদি আপনি 2 থেকে 10 টি আর্গুমেন্ট বলছেন, কোড হ্রাস হ'ল তাত্পর্যপূর্ণ - 1 টি যুক্তির সাথে 2x গুণ কম, 4 টি সাথে 2x, 3x দিয়ে 8x, 4 সাথে 10xx, 10 টি যুক্তি দিয়ে।
এখন, আমরা নিখুঁত ফরোয়ার্ডিং এবং SFINAE এর মাধ্যমে এটি পেতে পারি, আপনাকে একটি একক নির্মাণকারী বা ফাংশন টেম্পলেট লিখতে দেয় যা 10 টি আর্গুমেন্ট গ্রহণ করে, SFINAE আর্গুমেন্টগুলি উপযুক্ত ধরণের কিনা তা নিশ্চিত করার জন্য, এবং তারপরে সেগুলি মুভিং বা অনুলিপিগুলিতে স্থানান্তর করতে পারে does স্থানীয় রাষ্ট্র প্রয়োজন হিসাবে। যদিও এটি প্রোগ্রাম আকারের সমস্যাটিতে হাজারগুণ বৃদ্ধি রোধ করে, এখনও এই টেমপ্লেট থেকে উত্পন্ন ফাংশনগুলির পুরো গাদা থাকতে পারে। (টেম্পলেট ফাংশন ইনস্ট্যান্টেশনগুলি ফাংশন উত্পন্ন করে)
এবং প্রচুর উত্পন্ন ফাংশনগুলির অর্থ বৃহত্তর এক্সিকিউটেবল কোড আকার, যা নিজেই কর্মক্ষমতা হ্রাস করতে পারে।
কয়েকটি move
এসের ব্যয়ের জন্য আমরা সংক্ষিপ্ত কোড এবং প্রায় একই কার্যকারিতা পাই এবং প্রায়শই কোড বোঝা সহজ হয়।
এখন, এটি কেবলমাত্র কাজ করে কারণ আমরা জানি, যখন ফাংশনটি (এই ক্ষেত্রে কোনও কনস্ট্রাক্টর) বলা হয়, আমরা সেই যুক্তির স্থানীয় অনুলিপি চাইব। ধারণাটি হ'ল যদি আমরা জানতে পারি যে আমরা একটি অনুলিপি তৈরি করতে যাচ্ছি, আমাদের কলকারীকে জানিয়ে দেওয়া উচিত যে আমরা আমাদের যুক্তি তালিকায় রেখে একটি অনুলিপি তৈরি করছি। তারপরে তারা এই সত্যটি চারপাশে অনুকূল করতে পারে যে তারা আমাদের একটি অনুলিপি দিতে চলেছে (উদাহরণস্বরূপ আমাদের যুক্তিতে ডুবে)।
'বাই বাই ভ্যালু' কৌশলটির আরেকটি সুবিধা হ'ল প্রায়শই কনস্ট্রাক্টর মুভ কন্টাক্টর্টস That এর অর্থ হল যে ক্রিয়াকলাপগুলি যা মানকে গ্রহণ করে এবং তাদের যুক্তি থেকে সরে যায় প্রায়শই অযোগ্য হতে পারে, কোনও throw
শরীরকে তার দেহ এবং কলিং স্কোপে নিয়ে যায় often (যারা কখনও কখনও এটি সরাসরি নির্মাণের মাধ্যমে এড়াতে পারে, বা আইটেমগুলি তৈরি করতে এবং move
যুক্তিতে তৈরি করতে পারে যেখানে নিক্ষেপ ঘটে সেখানে নিয়ন্ত্রণ করতে পারে methods) পদ্ধতিগুলিকে নোহ্রো তৈরি করা প্রায়শই উপযুক্ত।