একটি প্রেরণকারী কাজ ঠিক কি?


198

সর্বাধিক এর বার , reentrance সংজ্ঞা থেকে উদ্ধৃত করা হয় উইকিপিডিয়া :

কোনও কম্পিউটার প্রোগ্রাম বা রুটিনটিকে প্রেরণকারী হিসাবে বর্ণনা করা হয় যদি এর আগের অনুরোধটি শেষ হওয়ার আগেই নিরাপদে আবার কল করা যায় (অর্থাত এটি নিরাপদে একই সাথে কার্যকর করা যেতে পারে)। কম্পিউটার প্রোগ্রাম বা রুটিনকে নতুন করে পাঠাতে হবে:

  1. কোনও স্থিতিশীল (বা গ্লোবাল) অ-ধ্রুবক ডেটা থাকতে হবে না।
  2. স্থিতিশীল (বা গ্লোবাল) অ স্থির ডেটাতে ঠিকানাটি ফেরৎ দেওয়া উচিত নয়।
  3. কলারের দ্বারা সরবরাহ করা ডেটাতে অবশ্যই কাজ করা উচিত।
  4. সিঙ্গলটন সংস্থানগুলিতে লকগুলির উপর নির্ভর করা উচিত নয়।
  5. অবশ্যই নিজস্ব কোডটি সংশোধন করবেন না (তার নিজস্ব অনন্য থ্রেড স্টোরেজটিতে চালিত না হওয়া পর্যন্ত)
  6. অ-পুনরায় কম্পিউটার প্রোগ্রাম বা রুটিনগুলিতে কল করা উচিত নয়।

নিরাপদে সংজ্ঞায়িত হয় কীভাবে ?

যদি কোনও প্রোগ্রাম একযোগে নিরাপদে সম্পাদন করা যায় তবে এর অর্থ কি সর্বদা এটি পুনরায় প্রেরণ করা হয়?

ছদ্ম দফার মধ্যে সাধারণ থ্রেডটি ঠিক কীটি উল্লেখ করা হয়েছে যে আমাকে পুনরায় প্রবেশকারীর ক্ষমতার জন্য আমার কোডটি পরীক্ষা করার সময় আমার মনে রাখা উচিত?

এছাড়াও,

  1. সমস্ত পুনরাবৃত্ত ফাংশন কি প্রতীক্ষিত হয়?
  2. সমস্ত থ্রেড-সেফ ফাংশন কি পুনরায় অনুপ্রবেশকারী?
  3. সমস্ত পুনরাবৃত্ত এবং থ্রেড-নিরাপদ ফাংশনগুলি কি প্রত্যাবর্তিত হয়?

এই প্রশ্নটি লেখার সময় একটি জিনিস মাথায় আসে: পুনরায় চাপানো এবং থ্রেড সুরক্ষার মতো পদগুলি কি একেবারে নিরঙ্কুশ ie এগুলির মধ্যে কি স্থির সিদ্ধান্ত রয়েছে? কারণ, যদি তারা না হয় তবে এই প্রশ্নটি খুব অর্থবহ নয়।


6
আসলে, আমি প্রথম তালিকায় # 2 এর সাথে একমত নই। আপনি পুনরায় প্রবেশকারী ফাংশন থেকে যা খুশি তে কোনও ঠিকানা ফিরিয়ে দিতে পারেন - কলিং কোডে সেই ঠিকানাটির সাথে সীমাবদ্ধতাটি আপনি কী করেন on

2
@ নীল তবে যেহেতু প্রেরণকারী ফাংশনটির লেখক নিয়ন্ত্রণ করতে পারবেন না, কলকারী নিশ্চয়ই তাদের সত্যিকারের পুনরায় অনুপ্রেরণার জন্য স্থির (বা বিশ্বব্যাপী) অ-ধ্রুবক ডেটাতে অবশ্যই কোনও ঠিকানা ফেরত দেবেন না?
রববেন_ফোর্ড_ ফ্যান_বয়

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

"থ্রেড-সেফ" অর্থহীন, যদি না আপনি থ্রেডগুলি কী করছে এবং তাদের কাজগুলির প্রত্যাশিত প্রভাব কী তা নির্দিষ্ট করে না। তবে সম্ভবত এটি একটি পৃথক প্রশ্ন হওয়া উচিত।

আমি নিরাপদে বোঝাতে চাই, সময়সূচি নির্বিশেষে আচরণটি ভালভাবে সংজ্ঞায়িত এবং নির্ধারক।
আতুরস্যামস

উত্তর:


191

1. নিরাপদে সংজ্ঞায়িত কীভাবে ?

শব্দার্থিক ভাবে। এই ক্ষেত্রে, এটি কোনও কঠোর সংজ্ঞাযুক্ত শব্দ নয়। এর অর্থ কেবল "ঝুঁকি ছাড়াই আপনি এটি করতে পারেন"।

২. যদি কোনও প্রোগ্রাম একযোগে নিরাপদে সম্পাদন করা যায় তবে এর অর্থ কি সর্বদা এটি পুনরায় প্রেরণকারী?

না।

উদাহরণস্বরূপ, আসুন একটি সি ++ ফাংশন থাকুন যা প্যারামিটার হিসাবে লক এবং কলব্যাক উভয়ই গ্রহণ করে:

#include <mutex>

typedef void (*callback)();
std::mutex m;

void foo(callback f)
{
    m.lock();
    // use the resource protected by the mutex

    if (f) {
        f();
    }

    // use the resource protected by the mutex
    m.unlock();
}

অন্য ফাংশনটির জন্য একই মুটেক্সটিকে লক করার দরকার হতে পারে:

void bar()
{
    foo(nullptr);
}

প্রথম দর্শনে, সবকিছু ঠিক আছে বলে মনে হচ্ছে ... তবে অপেক্ষা করুন:

int main()
{
    foo(bar);
    return 0;
}

যদি মিটেক্সে থাকা লকটি পুনরাবৃত্তি না হয় তবে মূল থ্রেডে এখানে কী ঘটবে তা এখানে:

  1. mainডাকবে foo
  2. foo লক অর্জন করবে
  3. fooকল করবে bar, যা ডাকবে foo
  4. দ্বিতীয়টি fooলকটি অর্জন করার চেষ্টা করবে, ব্যর্থ হবে এবং এটি প্রকাশের জন্য অপেক্ষা করবে।
  5. অচলাবস্থা।
  6. ওহো ...

ঠিক আছে, আমি কলব্যাক জিনিসটি ব্যবহার করে প্রতারণা করেছি। তবে কোডের আরও জটিল টুকরোগুলি একইরকম প্রভাব ফেলেছে তা কল্পনা করা সহজ।

৩. পুনরায় পাঠকের ক্ষমতার জন্য আমার কোডটি পরীক্ষা করার সময় আমার মনে রাখা উচিত যে উল্লিখিত ছয়টি দফার মধ্যে সাধারণ থ্রেডটি ঠিক কী?

আপনি করতে পারেন গন্ধ একটি সমস্যা আপনার ফাংশন আছে / একটি সংশোধনযোগ্য ক্রমাগত সম্পদ অ্যাক্সেস দেয়, অথবা হয়েছে / একটি ফাংশন যা একসেস দেয় গন্ধ পাচ্ছি

( ঠিক আছে, আমাদের কোডের 99% গন্ধ হওয়া উচিত, তারপরে ... এটি হ্যান্ডেল করার জন্য শেষ বিভাগটি দেখুন ... )

সুতরাং, আপনার কোড অধ্যয়ন করে, সেই পয়েন্টগুলির মধ্যে একটি আপনাকে সতর্ক করা উচিত:

  1. ফাংশনটির একটি রাষ্ট্র রয়েছে (যেমন একটি গ্লোবাল ভেরিয়েবল অ্যাক্সেস করুন, এমনকি কোনও শ্রেণীর সদস্যের ভেরিয়েবল)
  2. এই ফাংশনটি একাধিক থ্রেড দ্বারা ডাকা যেতে পারে, বা প্রক্রিয়াটি সম্পাদন করার সময় স্ট্যাকের মধ্যে দু'বার উপস্থিত হতে পারে (যেমন ফাংশনটি সরাসরি বা অপ্রত্যক্ষভাবে নিজেকে কল করতে পারে)। প্যারামিটার হিসাবে কলব্যাক নেওয়া ফাংশন প্রচুর গন্ধ পায়

নন-পুনঃপ্রবর্তনটি ভাইরাল: মনে রাখবেন যে এমন একটি ফাংশন যা কোনও সম্ভাব্য অ-পুনঃপ্রণালী ফাংশনটিকে কল করতে পারে তাকে পুনরায় তদন্তকারী হিসাবে বিবেচনা করা যায় না।

দ্রষ্টব্য, এছাড়াও, যে সি ++ পদ্ধতিগুলির গন্ধ তারা অ্যাক্সেস পেয়েছেthis , তাই আপনার কোনও মজাদার ইন্টারঅ্যাকশন না রয়েছে তা নিশ্চিত করার জন্য আপনার কোডটি অধ্যয়ন করা উচিত।

4.1। সমস্ত পুনরাবৃত্ত ফাংশন কি প্রতীক্ষিত হয়?

না।

মাল্টিথ্রেডেড ক্ষেত্রে, ভাগ করা সংস্থান অ্যাক্সেস করা একটি পুনরাবৃত্ত ফাংশন একই মুহুর্তে একাধিক থ্রেড দ্বারা কল করা যেতে পারে, ফলস্বরূপ খারাপ / দূষিত ডেটার ফলস্বরূপ।

একক থ্রেডযুক্ত ক্ষেত্রে, একটি পুনরাবৃত্ত ফাংশন একটি পুনঃপ্রেরণকারী ফাংশন (কুখ্যাত strtok) এর মতো ব্যবহার করতে পারে , বা ডেটা ইতিমধ্যে ব্যবহৃত হয়েছে তা হস্তান্তর না করে বৈশ্বিক ডেটা ব্যবহার করতে পারে। সুতরাং আপনার ফাংশনটি পুনরাবৃত্ত কারণ এটি সরাসরি বা অপ্রত্যক্ষভাবে নিজেকে কল করে তবে এটি পুনরাবৃত্ত-অনিরাপদ হতে পারে ।

4.2। সমস্ত থ্রেড-সেফ ফাংশন কি পুনরায় অনুপ্রবেশকারী?

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

4.3। সমস্ত পুনরাবৃত্ত এবং থ্রেড-নিরাপদ ফাংশনগুলি কি প্রত্যাবর্তিত হয়?

আমি "হ্যাঁ" বলব যদি "পুনরাবৃত্ত" দ্বারা আপনার অর্থ "পুনরাবৃত্ত-নিরাপদ" হয়।

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

সমস্যাটি এই গ্যারান্টিটি মূল্যায়ন করছে ... ^ _ ^ ^

৫. পুনরায় প্রবেশ এবং থ্রেড সুরক্ষার মতো পদগুলি কি একেবারে নিরঙ্কুশ, অর্থাৎ তাদের কি স্থির সংজ্ঞা রয়েছে?

আমি বিশ্বাস করি তারা করে, তবে তারপরে কোনও ফাংশনের মূল্যায়ন করা থ্রেড-সেফ বা পুনরায় প্রবর্তন করা কঠিন হতে পারে। এই কারণেই আমি উপরের গন্ধ শব্দটি ব্যবহার করেছি : আপনি খুঁজে পেতে পারেন যে কোনও ফাংশন পুনরায় প্রেরণকারী নয়, তবে জটিল জটিল কোডের পুনরায় প্রেরণকারী তা নিশ্চিত হওয়া কঠিন হতে পারে

6. একটি উদাহরণ

আসুন ধরে নেওয়া যাক আপনার একটি অবজেক্ট রয়েছে যার একটি পদ্ধতি রয়েছে যার জন্য কোনও সংস্থান ব্যবহার করা দরকার:

struct MyStruct
{
    P * p;

    void foo()
    {
        if (this->p == nullptr)
        {
            this->p = new P();
        }

        // lots of code, some using this->p

        if (this->p != nullptr)
        {
            delete this->p;
            this->p = nullptr;
        }
    }
};

প্রথম সমস্যাটি হ'ল যদি কোনওভাবে এই ফাংশনটিকে পুনরাবৃত্তভাবে বলা হয় (যেমন এই ফাংশনটি নিজেকে প্রত্যক্ষ বা অপ্রত্যক্ষভাবে কল করে), কোড সম্ভবত ক্রাশ this->pহবে , কারণ শেষ কলের শেষে মুছে ফেলা হবে, এবং সম্ভবত সম্ভবত শেষ হওয়ার আগে ব্যবহার করা হবে প্রথম কল

সুতরাং, এই কোডটি পুনরাবৃত্ত-নিরাপদ নয়

আমরা এটি সংশোধন করতে একটি রেফারেন্স কাউন্টার ব্যবহার করতে পারি:

struct MyStruct
{
    size_t c;
    P * p;

    void foo()
    {
        if (c == 0)
        {
            this->p = new P();
        }

        ++c;
        // lots of code, some using this->p
        --c;

        if (c == 0)
        {
            delete this->p;
            this->p = nullptr;
        }
    }
};

এইভাবে কোডটি পুনরাবৃত্ত-নিরাপদে পরিণত হয় ... তবে মাল্টিথ্রেডিং ইস্যুগুলির কারণে এটি এখনও তত্পর হয় না: আমাদের অবশ্যই নিশ্চিত হতে হবে যে একটি পুনরাবৃত্তিকারী মুটেক্স ব্যবহার করে cএবং এর সংশোধনগুলি পরমাণুভাবে করা হবে (সমস্ত মিউটেক্স পুনরাবৃত্ত নয়):p

#include <mutex>

struct MyStruct
{
    std::recursive_mutex m;
    size_t c;
    P * p;

    void foo()
    {
        m.lock();

        if (c == 0)
        {
            this->p = new P();
        }

        ++c;
        m.unlock();
        // lots of code, some using this->p
        m.lock();
        --c;

        if (c == 0)
        {
            delete this->p;
            this->p = nullptr;
        }

        m.unlock();
    }
};

এবং অবশ্যই, এই সব অনুমান lots of codeনিজেই ব্যবহার সমেত পুন: প্রবেশ হয় p

এবং উপরের কোডটি দূর থেকেও ব্যতিক্রম-নিরাপদ নয় , তবে এটি অন্য গল্প… ^ _ ^ ^

Hey. আরে আমাদের কোডের ৯৯% আবার তদন্তকারী নয়!

স্প্যাগেটি কোডের জন্য এটি বেশ সত্য। তবে আপনি যদি নিজের কোডটি সঠিকভাবে বিভাজন করেন তবে আপনি পুনরায় সমস্যা এড়াতে পারবেন।

7.1। নিশ্চিত করুন যে সমস্ত ক্রিয়াকলাপের কোনও রাজ্য নেই

তাদের কেবলমাত্র প্যারামিটারগুলি, তাদের নিজস্ব স্থানীয় ভেরিয়েবলগুলি, রাষ্ট্র ব্যতীত অন্যান্য ফাংশনগুলি এবং ডেটা অনুলিপিগুলি যদি কিছুটা ফিরে আসে তবে তাদের অবশ্যই ব্যবহার করতে হবে।

7.2। আপনার অবজেক্টটি "পুনরাবৃত্ত-নিরাপদ" কিনা তা নিশ্চিত করুন

একটি অবজেক্ট পদ্ধতিতে অ্যাক্সেস রয়েছে this, সুতরাং এটি অবজেক্টের একই উদাহরণের সমস্ত পদ্ধতির সাথে একটি স্টেট ভাগ করে।

সুতরাং, নিশ্চিত হয়ে নিন যে বস্তুটি স্ট্যাকের এক পর্যায়ে (যেমন কল করার পদ্ধতি এ) ব্যবহার করা যেতে পারে, এবং তারপরে, অন্য কোনও পয়েন্টে (অর্থাত্ বি কল করার পদ্ধতিটি) পুরো অবজেক্টকে কলুষিত না করেই ব্যবহার করা যেতে পারে। আপনার অবজেক্টটি এমনভাবে তৈরি করুন যে কোনও পদ্ধতিটি বেরিয়ে যাওয়ার পরে অবজেক্টটি স্থিতিশীল এবং সঠিক (কোনও ঝুঁকির পয়েন্টার নেই, সদস্যের বৈকল্পিকের বিরোধী নয় ইত্যাদি)।

7.3। আপনার সমস্ত বস্তু সঠিকভাবে আবদ্ধ হয়েছে তা নিশ্চিত করুন

অন্য কারওও অভ্যন্তরীণ তথ্য অ্যাক্সেস করা উচিত নয়:

    // bad
    int & MyObject::getCounter()
    {
        return this->counter;
    }

    // good
    int MyObject::getCounter()
    {
        return this->counter;
    }

    // good, too
    void MyObject::getCounter(int & p_counter)
    {
        p_counter = this->counter;
    }

এমনকি কনস্টের রেফারেন্সটি ফিরিয়ে দেওয়া বিপজ্জনক হতে পারে যদি ব্যবহারকারী ডেটার ঠিকানাটি পুনরুদ্ধার করে, কারণ কোডের অন্য কোনও অংশ কনস্টের রেফারেন্সটি না বলে কোডটি পরিবর্তন করতে পারে।

7.4। নিশ্চিত করুন যে ব্যবহারকারী জানেন যে আপনার জিনিসটি থ্রেড-নিরাপদ নয়

সুতরাং, ব্যবহারকারী থ্রেডগুলির মধ্যে ভাগ করে নেওয়া কোনও বস্তু ব্যবহারের জন্য মিউটেক্সগুলি ব্যবহার করার জন্য দায়বদ্ধ।

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

7.5। আপনার থ্রেড-সেফ কোডটি পুনরাবৃত্ত-নিরাপদ রয়েছে তা নিশ্চিত করুন

এর অর্থ পুনরাবৃত্তিমূলক মুটেক্সেস ব্যবহার করা যদি আপনি বিশ্বাস করেন যে একই সূত্রটি একই থ্রেড দ্বারা দু'বার ব্যবহার করা যেতে পারে।


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

আপনি কি প্রথম উদাহরণটিতে মিটেক্সে যেতে মিস করেছেন?
স্পষ্টত

@ পেয়ারসাবল: আপনার উদাহরণটি ভুল। আপনার আসলে কলব্যাক নিয়ে বিরক্ত করার দরকার নেই, একটি সাধারণ পুনরাবৃত্তি যদি একই থাকে তবে একই সমস্যা হবে তবে কেবল সমস্যাটি আপনি লকটি বরাদ্দ করা হয়েছে ঠিক তা বলতে ভুলে গেছেন।
Yttrill

3
@ ইয়িট্রিল: আমি ধরে নিয়েছি আপনি প্রথম উদাহরণটির বিষয়ে কথা বলছেন। আমি "কলব্যাক" ব্যবহার করেছি কারণ, সংক্ষেপে, একটি কলব্যাক গন্ধ পেয়েছে। অবশ্যই, একটি পুনরাবৃত্তি ফাংশন একই সমস্যা হতে পারে, তবে সাধারণত, কেউ সহজেই একটি ফাংশন এবং তার পুনরাবৃত্ত প্রকৃতি বিশ্লেষণ করতে পারে, এটি সনাক্ত করে এটি পুনরায় অনুবর্তনকারী কিনা বা পুনরাবৃত্তির জন্য এটি ঠিক আছে। অন্যদিকে, কলব্যাকের অর্থ হ'ল কলব্যাকটি কল করার ফাংশনের লেখকের কলব্যাক কী করছে সে সম্পর্কে কোনও তথ্য নেই, সুতরাং এই লেখক তার কাজটি পুনরায় অনুপ্রবেশ করে তা নিশ্চিত করতে অসুবিধা পেতে পারেন। এই অসুবিধাটি আমি প্রদর্শন করতে চেয়েছিলাম।
প্যারাসেবল

1
@ গ্যাব 是 好人: আমি প্রথম উদাহরণটি সংশোধন করেছি। ধন্যবাদ! একটি সিগন্যাল হ্যান্ডলার তার নিজস্ব সমস্যা নিয়ে আসত, পুনর্জাগরণ থেকে পৃথক, সাধারণত, যখন একটি সংকেত উত্থাপিত হয়, আপনি একটি নির্দিষ্টভাবে ঘোষিত বৈশ্বিক ভেরিয়েবল পরিবর্তন করার পরে সত্যই কিছু করতে পারবেন না।
প্যারাসেবল

21

"নিরাপদে" হ'ল সংজ্ঞাটি হুবহু সংজ্ঞায়িত হয় - এর অর্থ "অন্যান্য জিনিসে হস্তক্ষেপ না করে সঠিকভাবে এটি করা" means আপনি যে ছয়টি দফত উল্লেখ করেছেন তা অর্জনের প্রয়োজনীয়তাগুলি স্পষ্টভাবে প্রকাশ করে।

আপনার 3 টি প্রশ্নের উত্তর 3 × "না"।


সমস্ত পুনরাবৃত্ত ফাংশন কি প্রতীক্ষিত হয়?

না!

পুনরাবৃত্ত ক্রিয়াকলাপের দুটি যুগপত অনুরোধগুলি একে অপরকে সহজেই স্ক্রু করতে পারে, যদি তারা একই বৈশ্বিক / স্থিতিশীল ডেটা অ্যাক্সেস করে, উদাহরণস্বরূপ।


সমস্ত থ্রেড-সেফ ফাংশন কি পুনরায় অনুপ্রবেশকারী?

না!

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


সমস্ত পুনরাবৃত্ত এবং থ্রেড-নিরাপদ ফাংশনগুলি কি প্রত্যাবর্তিত হয়?

না!

উপরে দেখুন.


10

সাধারণ থ্রেড:

রুটিনটি বাধাগ্রস্থ হওয়ার সময় বলা হলে আচরণটি কি ভালভাবে সংজ্ঞায়িত হয়?

আপনার যদি এর মতো কোনও ফাংশন থাকে:

int add( int a , int b ) {
  return a + b;
}

তাহলে এটি কোনও বাহ্যিক অবস্থার উপর নির্ভরশীল নয়। আচরণ ভালভাবে সংজ্ঞায়িত করা হয়।

আপনার যদি এর মতো কোনও ফাংশন থাকে:

int add_to_global( int a ) {
  return gValue += a;
}

ফলাফল একাধিক থ্রেডে ভালভাবে সংজ্ঞায়িত হয়নি। যদি সময়টি ঠিক ভুল হয় তবে তথ্য হারাতে পারে।

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


7

এখন আমার আগের মন্তব্যটি বিস্তারিতভাবে বর্ণনা করতে হবে। পছন্দ করুন উদাহরণস্বরূপ কোডটিতে কেউ কি খেয়াল করতে পারেনি যে মূটেক্সটিকে প্যারামিটার বলে মনে করা হচ্ছে তা আসলে পাস হয়নি?

আমি উপসংহারটি নিয়ে বিতর্ক করি, আমি দৃ .়ভাবে বলছি: কোনও কার্যকারিতা সম্মতির সাথে উপস্থিত থাকার জন্য এটি পুনরায় প্রবেশ করতে হবে rant সুতরাং একযোগে-নিরাপদ (সাধারণত লিখিত থ্রেড-নিরাপদ) পুনরায় প্রবেশকারী বোঝায়।

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

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

এটি বুঝতে গুরুত্বপূর্ণ যে সাধারণভাবে থ্রেড-সেফ অপারেশনটিতে প্যারামিটারগুলি অন্তর্ভুক্ত করা বাজে কথা । আপনি যদি কোনও ডাটাবেস প্রোগ্রামিং করেন তবে আপনি বুঝতে পারবেন। "পারমাণবিক" কী এবং ধারণাটি মুটেক্স বা অন্য কোনও কৌশল দ্বারা সুরক্ষিত থাকতে পারে তা অবশ্যই একটি ব্যবহারকারী ধারণা: একটি ডাটাবেসে লেনদেন প্রক্রিয়াজাতকরণের জন্য একাধিক অ-বাধা পরিবর্তনগুলির প্রয়োজন হতে পারে। ক্লায়েন্ট প্রোগ্রামার ছাড়া কোনটি সিঙ্কে রাখা দরকার তা কে বলতে পারে?

মুল বক্তব্যটি হ'ল "দুর্নীতি" আপনার কম্পিউটারে অপ্রচলিত লেখার সাথে স্মৃতি জাগ্রত করতে হবে না: সমস্ত স্বতন্ত্র ক্রিয়াকলাপ সিরিয়ালাইজড হয়ে গেলেও দুর্নীতি হতে পারে। এটি অনুসরণ করে যে আপনি যখন জিজ্ঞাসা করছেন যে কোনও ফাংশন থ্রেড-নিরাপদ, বা পুনরায় প্রবেশকারী, প্রশ্নটির অর্থ যথাযথভাবে পৃথক হওয়া সমস্ত যুক্তিগুলির জন্য: যুগল যুক্তি ব্যবহার করে কোনও পাল্টা উদাহরণ তৈরি হয় না।

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

একটি ভাল উদাহরণ malloc হয়। এটি পুনরায় প্রবেশকারী নয় এবং থ্রেড-নিরাপদ নয়। এর কারণ এটি একটি বৈশ্বিক সংস্থান (গাদা) অ্যাক্সেস করতে হবে। লক ব্যবহার করা নিরাপদ করে না: এটি অবশ্যই পুনরায় প্রবেশকারী নয়। যদি ম্যালোকের ইন্টারফেসটি সঠিকভাবে ডিজাইন করা হত তবে এটি পুনরায় প্রবেশকারী এবং থ্রেড-নিরাপদ করা সম্ভব হবে:

malloc(heap*, size_t);

এখন এটি নিরাপদ হতে পারে কারণ এটি ক্লায়েন্টের কাছে একটি একক apগলে ভাগ করে নেওয়া অ্যাক্সেসকে সিরিয়াল করার জন্য দায়িত্ব স্থানান্তর করে। বিশেষত কোনও পৃথক হ্যাপ অবজেক্ট থাকলে কোনও কাজের প্রয়োজন হয় না। যদি একটি সাধারণ গাদা ব্যবহৃত হয় তবে ক্লায়েন্টকে অ্যাক্সেস সিরিয়াল করতে হবে। ফাংশনের অভ্যন্তরে একটি লক ব্যবহার করা যথেষ্ট নয়: কেবলমাত্র একটি মলোককে একটি গাদা * লক করা বিবেচনা করুন এবং তারপরে একটি সংকেত উপস্থিত হবে এবং একই পয়েন্টারে ম্যালোককে কল করুন: অচলাবস্থা: সংকেতটি এগিয়ে যেতে পারে না, এবং ক্লায়েন্ট হয় না কারণ এটি বাধা দেওয়া হয়।

সাধারণভাবে বলতে গেলে, লকগুলি জিনিসগুলিকে থ্রেড-নিরাপদ করে না ... ক্লায়েন্টের মালিকানাধীন এমন কোনও সংস্থান পরিচালনা করার জন্য অনুপযুক্তভাবে চেষ্টা করে তারা সুরক্ষাটি ধ্বংস করে। লকিংটি অবজেক্ট প্রস্তুতকারকের দ্বারা সম্পন্ন করতে হবে, কেবলমাত্র কোডটি জানে যে কতগুলি অবজেক্ট তৈরি করা হয়েছে এবং সেগুলি কীভাবে ব্যবহৃত হবে তা জানে।


"সুতরাং সমবর্তী-নিরাপদ (সাধারণত লিখিত থ্রেড-নিরাপদ) পুনরায় প্রবেশকারীকে বোঝায়" " এটি "থ্রেড-নিরাপদ তবে প্রত্যাবর্তক নয়" উইকিপিডিয়া উদাহরণের সাথে বিরোধিতা করে ।
ম্যাগগিরো

3

তালিকাভুক্ত পয়েন্টগুলির মধ্যে "প্রচলিত থ্রেড" (শঙ্কিত উদ্দেশ্য !?) হ'ল ফাংশনটি এমন কোনও কাজ না করে যা একই ফাংশনে কোনও পুনরাবৃত্ত বা সমবর্তী কলগুলির আচরণকে প্রভাবিত করে।

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

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

যা বলেছিল, বিন্দু (1) অগত্যা সত্য নয়; উদাহরণস্বরূপ, আপনি বৈধভাবে এবং ডিজাইনের সাহায্যে অতিরিক্ত পুনরাবৃত্তি থেকে রক্ষা করতে বা একটি অ্যালগরিদম প্রোফাইল করতে পুনরাবৃত্তি গণনা ধরে রাখতে একটি স্ট্যাটিক ভেরিয়েবল ব্যবহার করতে পারেন।

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


1

আপনার "এছাড়াও" প্রশ্নের উত্তরগুলি হ'ল "না", "না" এবং "না"। কোনও ফাংশন পুনরাবৃত্ত এবং / বা থ্রেড নিরাপদ কারণ এটি পুনরায় প্রবেশকারী হয় না।

এই ধরণের প্রতিটি ফাংশন আপনার উদ্ধৃত সমস্ত পয়েন্টে ব্যর্থ হতে পারে। (যদিও আমি পয়েন্ট 5 এর 100% নির্দিষ্ট না)।


1

"থ্রেড-নিরাপদ" এবং "পুনরায় প্রবেশকারী" পদগুলির অর্থ কেবল এবং তাদের সংজ্ঞাগুলি যা ঠিক তা বোঝায়। এই প্রসঙ্গে "নিরাপদ" এর অর্থ আপনি এর নীচে যে সংজ্ঞাটি উদ্ধৃত করেছেন কেবল তার অর্থ ।

"নিরাপদ" এখানে অবশ্যই বিস্তৃত অর্থে নিরাপদ নয় যে প্রদত্ত প্রসঙ্গে একটি প্রদত্ত ফাংশনটি কল করা আপনার অ্যাপ্লিকেশনটিকে পুরোপুরি হোসে করবে না। সামগ্রিকভাবে, একটি ফাংশন নির্ভরযোগ্যভাবে আপনার বহু-থ্রেড অ্যাপ্লিকেশনটিতে একটি পছন্দসই প্রভাব তৈরি করতে পারে তবে সংজ্ঞা অনুযায়ী পুনরায় প্রবেশকারী বা থ্রেড-নিরাপদ হিসাবে যোগ্য নয়। বিপরীতে, আপনি পুনরায় প্রবেশকারী ফাংশনগুলিকে কল করতে পারেন যেগুলি আপনার মাল্টি-থ্রেড অ্যাপ্লিকেশনটিতে বিভিন্ন ধরণের অনাকাঙ্ক্ষিত, অপ্রত্যাশিত এবং / বা অনির্দেশ্য প্রভাব তৈরি করবে।

রিকার্সিভ ফাংশন যে কোনও কিছু হতে পারে এবং পুনরায় প্রবেশকারীর থ্রেড-সেফের চেয়ে আরও শক্তিশালী সংজ্ঞা রয়েছে সুতরাং আপনার সংখ্যাযুক্ত প্রশ্নের উত্তরগুলি হ'ল না।

পুনরায় প্রবেশের সংজ্ঞাটি পড়া, যেহেতু এটির সংক্ষিপ্তসার হতে পারে এমন একটি ফাংশন যার অর্থ আপনি এটির পরিবর্তনের জন্য যা বলছেন তার বাইরে কোনও কিছুই সংশোধন করবে না। তবে আপনার কেবল সংক্ষিপ্তসার উপর নির্ভর করা উচিত নয়।

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

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