Message Passing এবং Synchronization

Parrot Concurrency এবং Parallelism (কনকারেন্সি এবং প্যারালেলিজম) - প্যারট (Parrot) - Computer Programming

274

Message Passing এবং Synchronization হল কম্পিউটার সিস্টেম, মাল্টি-থ্রেডেড এবং মাল্টি-প্রসেস প্রোগ্রামিংয়ের গুরুত্বপূর্ণ ধারণা, যা একাধিক প্রসেস বা থ্রেডের মধ্যে সমন্বয় এবং যোগাযোগ ব্যবস্থাপনা করতে ব্যবহৃত হয়। এই দুটি ধারণা সাধারণত Concurrency বা Parallelism নির্ধারণের জন্য ব্যবহৃত হয়, যেখানে একাধিক কার্যক্রম (processes বা threads) একে অপরের সাথে যোগাযোগ করে এবং সমন্বিতভাবে কাজ করে।

Message Passing (মেসেজ পাসিং)

Message Passing হল একাধিক প্রসেস বা থ্রেডের মধ্যে তথ্য বা বার্তা আদান-প্রদান করার পদ্ধতি। এটি একাধিক প্রসেস বা থ্রেডকে একে অপরের সাথে যোগাযোগ করতে সক্ষম করে, যেখানে এক বা একাধিক প্রসেসের মধ্যে কোনো ডেটা বা নির্দেশ পাস করা হয়।

Message Passing প্রক্রিয়ায়, একটি প্রসেস Message পাঠায় এবং অন্য প্রসেস সেই মেসেজ গ্রহণ করে তা প্রক্রিয়া করে। এটি দুটি ধরনের হতে পারে:

  1. Direct Communication (সরাসরি যোগাযোগ):
    • এখানে দুটি প্রসেস সরাসরি একে অপরের সাথে যোগাযোগ করে। অর্থাৎ, একটি প্রসেস অন্য প্রসেসে বার্তা পাঠানোর সময় সেই প্রসেসের ঠিকানা সরাসরি জানে।
  2. Indirect Communication (পরোক্ষ যোগাযোগ):
    • এখানে বার্তাটি একটি Message Queue বা Buffer ব্যবহার করে পাঠানো হয়। এক প্রসেস বার্তা পাঠায় এবং অন্য প্রসেস সেই বার্তা গ্রহণ করে।

Message Passing একাধিক প্রসেসের মধ্যে একে অপরের সাথে সংযুক্ত হতে সাহায্য করে, এবং এতে shared memory ব্যবহারের প্রয়োজন নেই। এটি মূলত distributed systems বা multitasking পরিবেশে ব্যবহৃত হয়, যেখানে একাধিক প্রসেস বা কম্পিউটার একে অপরের সাথে যোগাযোগ করতে হয়।

Message Passing এর উদাহরণ:

ধরা যাক, একটি সার্ভার ক্লায়েন্টে মেসেজ পাস করছে:

import multiprocessing

def worker(conn):
    message = conn.recv()  # মেসেজ গ্রহণ
    print(f"Received message: {message}")
    conn.send("Hello from worker")  # মেসেজ পাঠানো

if __name__ == '__main__':
    parent_conn, child_conn = multiprocessing.Pipe()  # দুইটি পিপ তৈরি
    p = multiprocessing.Process(target=worker, args=(child_conn,))
    p.start()

    parent_conn.send("Hello from parent")  # প্যারেন্ট প্রসেস থেকে মেসেজ পাঠানো
    print(f"Parent received: {parent_conn.recv()}")  # প্যারেন্ট প্রসেস থেকে মেসেজ গ্রহণ

    p.join()

এখানে, Pipe ব্যবহৃত হয়েছে যা দুটি প্রসেসের মধ্যে বার্তা পাঠানোর জন্য একটি পদ্ধতি। parent_conn প্যারেন্ট প্রসেস থেকে বার্তা পাঠিয়ে এবং গ্রহণ করে, এবং child_conn সন্তান প্রসেসে ব্যবহৃত হচ্ছে।

Synchronization (সিঙ্ক্রোনাইজেশন)

Synchronization হল একাধিক প্রসেস বা থ্রেডের মধ্যে কার্যক্রমের সঠিকভাবে সম্পাদন নিশ্চিত করার পদ্ধতি। যখন একাধিক থ্রেড বা প্রসেস একই রিসোর্সে একযোগে অ্যাক্সেস করতে চায়, তখন সিঙ্ক্রোনাইজেশন প্রয়োজন, যাতে রেস কন্ডিশন (race condition) বা ডেটার ইনকনসিস্টেন্সি (data inconsistency) না ঘটে।

প্রধানত critical section নামে পরিচিত যে কোনো কোড বা রিসোর্স যেখানে একাধিক থ্রেড বা প্রসেস একসাথে অ্যাক্সেস করার চেষ্টা করতে পারে, সেখানে সিঙ্ক্রোনাইজেশন গুরুত্বপূর্ণ। সিঙ্ক্রোনাইজেশন ব্যবহার না করলে একাধিক থ্রেড বা প্রসেস একই সময়ে একটি রিসোর্স অ্যাক্সেস করার চেষ্টা করতে পারে, যার ফলে ডেটার অপ্রত্যাশিত পরিবর্তন হতে পারে।

Synchronization এর মূল পদ্ধতি:

  1. Mutex (Mutual Exclusion):
    • Mutex একটি সিঙ্ক্রোনাইজেশন অবজেক্ট যা শুধুমাত্র একটি থ্রেড বা প্রসেসকে critical section-এ এক্সেস করতে দেয়। যখন একটি থ্রেড বা প্রসেস mutex অর্জন করে, অন্যথায় অন্য থ্রেড বা প্রসেস অপেক্ষা করতে থাকে।
  2. Semaphores:
    • Semaphore হলো একটি সিঙ্ক্রোনাইজেশন প্রক্রিয়া যা থ্রেড বা প্রসেসের সংখ্যা নিয়ন্ত্রণ করতে ব্যবহার করা হয়। এটি একটি কাউন্টার হিসেবেও কাজ করে, যার মাধ্যমে নির্দিষ্ট পরিমাণ থ্রেড বা প্রসেস একসাথে কাজ করতে পারে।
  3. Monitors:
    • Monitor হল একটি উচ্চ স্তরের সিঙ্ক্রোনাইজেশন কনসেপ্ট, যা সাধারণত অবজেক্ট-ওরিয়েন্টেড প্রোগ্রামিং ভাষায় ব্যবহৃত হয়। এটি একটি অবজেক্টের ভেতরে একাধিক থ্রেডের সিঙ্ক্রোনাইজেশন সহজ করে।

Synchronization এর উদাহরণ:

নীচের উদাহরণে, threading এবং Lock ব্যবহৃত হয়েছে যাতে একাধিক থ্রেডের মধ্যে সিঙ্ক্রোনাইজেশন নিশ্চিত করা যায়:

import threading

# Shared resource
counter = 0
lock = threading.Lock()

def increment():
    global counter
    with lock:  # Locking the critical section
        for _ in range(100000):
            counter += 1

def decrement():
    global counter
    with lock:  # Locking the critical section
        for _ in range(100000):
            counter -= 1

if __name__ == "__main__":
    thread1 = threading.Thread(target=increment)
    thread2 = threading.Thread(target=decrement)

    thread1.start()
    thread2.start()

    thread1.join()
    thread2.join()

    print("Final counter value:", counter)

এখানে, lock ব্যবহৃত হয়েছে যাতে একসাথে একাধিক থ্রেড একই counter ভেরিয়েবলকে পরিবর্তন না করে। যখন একটি থ্রেড lock অর্জন করে, অন্যথায় অন্য থ্রেড তা গ্রহণ করতে পারবে না।

Message Passing এবং Synchronization এর পার্থক্য

  1. Message Passing:
    • এটি একাধিক প্রসেস বা থ্রেডের মধ্যে তথ্য আদান-প্রদান করার জন্য ব্যবহৃত হয়।
    • একে distributed systems বা multi-processing environments-এ বেশি ব্যবহার করা হয়।
    • এতে shared memory ব্যবহৃত হয় না, বরং ডেটা বার্তা হিসেবে একে অপরের মধ্যে পাস করা হয়।
  2. Synchronization:
    • এটি একাধিক থ্রেড বা প্রসেসের মধ্যে সঠিকভাবে কার্যক্রম সম্পাদন নিশ্চিত করার জন্য ব্যবহৃত হয়।
    • এটি বিশেষভাবে একাধিক থ্রেড বা প্রসেস যখন একই রিসোর্স একসাথে অ্যাক্সেস করতে চায়, তখন প্রয়োগ করা হয়।
    • সিঙ্ক্রোনাইজেশন shared memory-এর নিরাপত্তা এবং কার্যকারিতা নিশ্চিত করে।

সারাংশ

  • Message Passing হল একাধিক প্রসেস বা থ্রেডের মধ্যে বার্তা আদান-প্রদান করার একটি পদ্ধতি, যা distributed systems এবং parallel computing-এ ব্যবহৃত হয়।
  • Synchronization হল একাধিক থ্রেড বা প্রসেসের মধ্যে সঠিক কার্যক্রম নিশ্চিত করার পদ্ধতি, যা race conditions প্রতিরোধ এবং critical section নিরাপদ করার জন্য ব্যবহৃত হয়।
  • Message Passing এবং Synchronization একসাথে ব্যবহৃত হয় যখন বিভিন্ন প্রসেস বা থ্রেডের মধ্যে সমন্বয় এবং কার্যকারিতা বজায় রাখতে হয়।
Content added By
Promotion

Are you sure to start over?

Loading...