সি ++ 11 থ্রেড_লোকাল ভেরিয়েবলগুলি স্বয়ংক্রিয়ভাবে স্থিতিশীল?


85

এই দুটি কোড বিভাগের মধ্যে কোনও পার্থক্য রয়েছে:

void f() {
    thread_local vector<int> V;
    V.clear();
    ... // use V as a temporary variable
}

এবং

void f() {
    static thread_local vector<int> V;
    V.clear();
    ... // use V as a temporary variable
}

ব্যাকস্টোরি: মূলত আমার স্ট্যাটিক ভেক্টর ভি ছিল (কিছু মধ্যবর্তী মান রাখার জন্য, আমি যখন ফাংশনে প্রবেশ করি তখন এটি পরিষ্কার হয়ে যায়) এবং একটি একক থ্রেডেড প্রোগ্রাম। আমি প্রোগ্রামটি একটি বহুবিধে পরিণত করতে চাই, তাই কোনওভাবে আমাকে এই স্থিতিশীল সংশোধক থেকে মুক্তি দিতে হবে। আমার ধারণাটি প্রতিটি স্ট্যাটিককে থ্রেড_লোকলে পরিণত করা এবং অন্য কিছুর জন্য চিন্তা করা উচিত নয়? এই পন্থা backfire করতে পারেন?


17
একটি thread_localস্থানীয় ভেরিয়েবল থাকা শুরু করার কোনও মানে নেই ... প্রতিটি থ্রেডের নিজস্ব কল স্ট্যাক রয়েছে।
কনরাড রুডল্ফ

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

4
@Konrad রুডলফ স্থানীয় ভেরিয়েবল কেবলমাত্র যেমন প্রকাশক staticবদলে static thread_localপ্রতিটি থ্রেড জন্য পরিবর্তনশীল এক উদাহরণ হিসেবে বলা যায় আরম্ভ করে না।
ডেভিড

4
@ ডেভিড এটি আমার বা ওপি উভয়েরই মূল বিষয় নয়। আমরা যে বিষয়ে কথা না staticবনাম static thread_localবরং সম্পর্কে autoবনাম thread_local, প্রাক সি ++ 11 অর্থ ব্যবহার auto(অর্থাত স্বয়ংক্রিয় স্টোরেজ)।
কনরাড রুডল্ফ

4
এছাড়াও থ্রেড-স্থানীয় স্থানীয় স্ট্যাটিক ভেরিয়েবলগুলি কীভাবে সংজ্ঞায়িত করবেন? । একটি দ্রুত ভাষার আইনজীবী নোট ... মাইক্রোসফ্ট এবং টিএলএস সমর্থন ভিস্তার চারপাশে পরিবর্তিত হয়েছে; দেখুন থ্রেড স্থানীয় সঞ্চয় (TLS) । পরিবর্তনটি সিঙ্গলটনের মতো জিনিসগুলিকে প্রভাবিত করে এবং প্রয়োগ করতেও পারে বা নাও পারে। আপনি যদি অ্যান্ডওয়ারওয়্যার সফ্টওয়্যার মডেল ব্যবহার করছেন তবে আপনি সম্ভবত ঠিক আছেন। আপনি যদি একাধিক সংকলক এবং প্ল্যাটফর্ম সমর্থন করে খুশি হন তবে আপনাকে এতে মনোযোগ দিতে হতে পারে।
jww

উত্তর:


94

সি ++ স্ট্যান্ডার্ড অনুসারে

থ্রেড_লোকাল যখন ব্লক স্কোপের একটি পরিবর্তনশীলটিতে প্রয়োগ করা হয় তখন স্টোরেজ-শ্রেণি-নির্দিষ্টকরণকারী স্ট্যাটিকটি স্পষ্টভাবে উপস্থিত না হলে তা বোঝানো হয়

সুতরাং এটি এর অর্থ এই সংজ্ঞা

void f() {
    thread_local vector<int> V;
    V.clear();
    ... // use V as a temporary variable
}

সমতুল্য

void f() {
    static thread_local vector<int> V;
    V.clear();
    ... // use V as a temporary variable
}

তবে একটি স্ট্যাটিক ভেরিয়েবল থ্রেড_লোকাল ভেরিয়েবলের সমান নয়

থ্রেড_লোকাল কীওয়ার্ড সহ 1 টি ঘোষিত সমস্ত ভেরিয়েবলের থ্রেড স্টোরেজ সময়কাল। এই সত্তাগুলির জন্য স্টোরেজ থ্রেড তৈরি হওয়ার সময়কালের জন্য স্থায়ী হবে। প্রতি থ্রেডে আলাদা আলাদা অবজেক্ট বা রেফারেন্স রয়েছে এবং ঘোষিত নামের ব্যবহারটি বর্তমান থ্রেডের সাথে সম্পর্কিত সত্তাকে বোঝায়

এই ভেরিয়েবলগুলি পার্থক্য করতে স্ট্যান্ডার্ড স্ট্যাটিক স্টোরেজ সময়কাল সহ একটি নতুন শব্দ থ্রেড স্টোরেজ সময়কাল পরিচয় করিয়ে দেয় ।


4
staticএবং externএইভাবে স্টোরেজ শ্রেণি বোঝায় না কেবল কেবল থ্রেড_লোকাল ভেরিয়েবলের জন্য এমনকি অভ্যন্তরীণ স্কোপগুলিতে লিঙ্কেজ।
উত্সাহক

4
@ ডিডুকুলেটর ব্লক স্কোপ ভেরিয়েবলের কোনও যোগসূত্র নেই। সুতরাং আপনার জীবনবৃত্তান্ত ভুল। আমি পোস্টে যেমন লিখেছি তাদের থ্রেড স্টোরেজ সময়কাল আছে। এটি বাস্তবে স্ট্যাটিক স্টোরেজ সময়কালের মতো তবে প্রতিটি থ্রেডে প্রয়োগ করা হয়।
মস্কো থেকে ভ্লাদ 19

4
আপনি যদি বাহ্যিক যোগ করেন তবে আপনি একটি ঘোষণা করছেন যা সংজ্ঞা নয়। তাহলে?
অনুদানকারক

4
@ ডেডুপ্লিকেটর সুতরাং এর অর্থ ব্লক স্কোপ ভেরিয়েবলের সংজ্ঞাগুলির কোনও যোগসূত্র নেই।
মস্কো থেকে ভ্লাদ

4
আমি কেবল এটি চেষ্টা করেছি যে ভিএস 2013 এ এবং এটি "টিএল ভেরিয়েবলগুলি গতিশীলভাবে আরম্ভ করা যায় না" বলে চিৎকার করে। আমি হতবাক
v.oddou

19

হ্যাঁ, "থ্রেড-লোকাল স্টোরেজ" "গ্লোবাল" (বা "স্ট্যাটিক স্টোরেজ") এর সাথে খুব মিল, কেবলমাত্র "পুরো প্রোগ্রামের সময়কাল" এর পরিবর্তে আপনার "পুরো থ্রেডের সময়কাল" থাকে। সুতরাং একটি ব্লক-স্থানীয় থ্রেড-লোকাল ভেরিয়েবল প্রথমবারের নিয়ন্ত্রণটি তার ঘোষণার মধ্য দিয়ে প্রারম্ভিক হয় তবে প্রতিটি থ্রেডের মধ্যে পৃথক করে এবং থ্রেডটি শেষ হয়ে গেলে এটি ধ্বংস হয়।


6

এর সাথে ব্যবহার করা হলে thread_local, staticক্লাস সদস্যের জন্য প্রয়োজনীয়, ব্লক-স্কোপে (@ ভ্লাদ এর উত্তর দেখুন) অন্তর্ভুক্ত থাকে; আমার ধারণা, নামের স্থানের সুযোগের যোগসূত্র।

9.2 / 6 প্রতি:

শ্রেণীর সংজ্ঞার মধ্যে কোনও সদস্যকে থ্রেড_লোকাল স্টোরেজ-শ্রেণি-নির্দিষ্টকারীর সাথে ঘোষণা করা হবে না যতক্ষণ না স্থিরও ঘোষণা করা হয়

মূল প্রশ্নের উত্তর দিতে:

সি ++ 11 থ্রেড_লোকাল ভেরিয়েবলগুলি স্বয়ংক্রিয়ভাবে স্থিতিশীল?

নেমস্পেস-স্কোপ ভেরিয়েবলগুলি বাদে কোনও বিকল্প নেই।

এই দুটি কোড বিভাগের মধ্যে কোনও পার্থক্য রয়েছে:

না


4

থ্রেড লোকাল স্টোরেজ স্থির তবে এটি সাধারণ স্ট্যাটিক স্টোরেজ থেকে একেবারেই আলাদা আচরণ করে।

আপনি যখন কোনও ভেরিয়েবল স্ট্যাটিক ঘোষণা করেন তখন ভেরিয়েবলের ঠিক এক উদাহরণ থাকে one সংকলক / রানটাইম সিস্টেম গ্যারান্টি দেয় যে এটি ব্যবহার করার আগে এটি আপনার জন্য কিছুক্ষণ শুরু করা হবে, ঠিক কখন নির্দিষ্ট করা ছাড়াই (এখানে কিছু বিশদ বাদ দেওয়া আছে))

সি ++ 11 গ্যারান্টি দেয় যে এই সূচনাটি থ্রেড নিরাপদ থাকবে, তবে সি ++ 11 এর আগে এই থ্রেড সুরক্ষার নিশ্চয়তা ছিল না। উদাহরণ স্বরূপ

static X * pointer = new X;

একসাথে একাধিক থ্রেড স্থিতিশীল সূচনার কোডটি হিট করলে এক্স এর উদাহরণ ফাঁস হতে পারে।

আপনি যখন কোনও ভেরিয়েবল থ্রেড স্থানীয় ঘোষণা করেন সেখানে ভেরিয়েবলের সম্ভাব্য সংখ্যার উদাহরণ রয়েছে। থ্রেড-আইডির সাহায্যে সূচিত হওয়া মানচিত্রে আপনি তাদের ভাবতে পারেন। তার মানে প্রতিটি থ্রেড ভেরিয়েবলের নিজস্ব কপিটি দেখে।

আবারও, যদি ভেরিয়েবলটি আরম্ভ হয় সংকলক / রানটাইম সিস্টেম গ্যারান্টি দেয় যে ডেটা ব্যবহারের আগে এই আরম্ভ হবে এবং ভেরিয়েবল ব্যবহারকারী প্রতিটি থ্রেডের জন্য আরম্ভ হবে initial সংকলকটি গ্যারান্টি দেয় যে দীক্ষা থ্রেড নিরাপদ থাকবে।

থ্রেড সুরক্ষার গ্যারান্টিটির অর্থ হল যে ভেরিয়েবলটি আপনি যেভাবে প্রত্যাশা করেন সেভাবে আচরণ করতে পর্দার কোডের বেশ কিছুটা পিছনে থাকতে পারে - বিশেষত বিবেচনা করে যে সংকলকটির ঠিক আগে কত থ্রেড হবে তা জানার উপায় নেই আপনার প্রোগ্রামে বিদ্যমান এবং এর মধ্যে কতগুলি থ্রেড স্থানীয় ভেরিয়েবলকে স্পর্শ করবে।


@ ইথেরিয়লোন: আকর্ষণীয়। কোন বিশেষ তথ্য? আপনি একটি রেফারেন্স প্রদান করতে পারেন?
ডেল উইলসন

4
stackoverflow.com/a/8102145/1576556 । উইকিপিডিয়া সি ++ 11 নিবন্ধটিতে উল্লেখ আছে যদি আমি সঠিক মনে করি।
ইথেরিয়লোনে

4
তবে স্থির বস্তুগুলি প্রথমে শুরু করা হয়, তারপরে অনুলিপি করা হয়। সুতরাং থ্রেড-নিরাপদ সূচনাতে সম্পূর্ণ এক্সপ্রেশন অন্তর্ভুক্ত কিনা তাও আমি কিছুটা অস্পষ্ট। এটি সম্ভবত এটির কারণ এটি অন্যথায় এটি থ্রেড-নিরাপদ হিসাবে বিবেচিত হবে না।
ইথেরিয়লোনে
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.