পাঠ ০৭ · ৫৭-এর মধ্যে · মডিউল ১
Home / Courses / Computer Architecture & Digital Logic / ইউনিভার্সাল গেট

ইউনিভার্সাল গেট — NAND ও NOR

Universal gates — NAND and NOR
৭ মিনিট পড়া শুরু · Beginner Python কোডসহ সম্পূর্ণ বাংলায়

এই পাঠে যা শিখবেন

  • "ইউনিভার্সাল গেট" মানে কী, এবং NAND/NOR কেন এই বৈশিষ্ট্য রাখে
  • NAND থেকে ধাপে ধাপে NOT, AND, OR বানানোর সূত্র ও যুক্তি
  • NOR দিয়েও একই কাজ কীভাবে হয় (সংক্ষেপে)
  • বাস্তব চিপ ডিজাইনে কেন প্রায়ই একটিমাত্র গেট টাইপ ব্যবহার করা হয়
  • Python কোডে শুধু NAND লিখে, তা দিয়েই NOT/AND/OR বানিয়ে, পূর্ণ ট্রুথ টেবিল মিলিয়ে যাচাই করা

১ · ইউনিভার্সাল গেট কী ও কেন গুরুত্বপূর্ণ

L04-এ AND, OR, NOT — এই তিনটি মৌলিক গেট শেখানো হয়েছিল, আর L01-এই সংক্ষেপে NANDNOT-ANDAND গেটের ঠিক উল্টো ফলাফল — দুটি ইনপুটই ১ হলে আউটপুট ০, বাকি সব ক্ষেত্রে আউটপুট ১।-এর উল্লেখ এসেছিল। এখন একটি চমকপ্রদ, বাস্তবিকভাবে গুরুত্বপূর্ণ সত্য দেখা যাক — শুধুমাত্র NAND গেট ব্যবহার করে, অন্য কোনো গেট টাইপ ছাড়াই, যেকোনো বুলিয়ান ফাংশন বানানো সম্ভব। এই বৈশিষ্ট্যকে বলা হয় ইউনিভার্সালিটি (universality)। NAND ও NORNOT-OROR গেটের ঠিক উল্টো ফলাফল — দুটি ইনপুটের অন্তত একটি ১ হলে আউটপুট ০, দুটোই ০ হলে আউটপুট ১। — দুটো গেটই এই বৈশিষ্ট্য রাখে (AND, OR, NOT এককভাবে এই বৈশিষ্ট্য রাখে না — যেমন শুধু AND গেট দিয়ে কখনোই NOT বানানো যায় না)।

কেন এটা গুরুত্বপূর্ণ? এই পাঠে NAND-এর জন্য এই দাবিটা শুধু বলে যাওয়া হবে না — কোডে বাস্তবিকভাবে প্রমাণ করে দেখানো হবে।

২ · NAND দিয়ে NOT, AND, OR বানানো

তিনটি ধাপে, তিনটি সূত্র দিয়ে NAND থেকে বাকি সব মৌলিক গেট বানানো যায় —

NOT(A) = NAND(A, A)
NAND-এর দুই ইনপুটকেই একসাথে বেঁধে (tie together) দিলে, ফলাফল ঠিক NOT-এর মতো আচরণ করে — A=1 হলে NAND(1,1)=0, A=0 হলে NAND(0,0)=1।
AND(A,B) = NOT(NAND(A,B))
NAND-এর আউটপুটকে আবার NAND(x,x) দিয়ে ইনভার্ট করলেই (উপরের NOT সূত্র প্রয়োগ করে) তা AND-এর সমতুল্য — "NOT-AND-এর NOT" আসলে বিশুদ্ধ AND।
OR(A,B) = NAND(NOT A, NOT B)
De Morgan's Law-এর (L05) সরাসরি প্রয়োগ — ¬A + ¬B ধরনের একটি এক্সপ্রেশন হিসেবে দেখলে এটি ঠিক OR-এর সমতুল্য বের করে দেয়।
NAND(A,B) — একমাত্র প্রিমিটিভ NOT(A) = NAND(A, A) AND(A,B) = NOT(NAND(A,B)) OR(A,B) = NAND(NOT A, NOT B) তিনটিই শুধুমাত্র NAND-এর একাধিক কল দিয়ে গঠিত — কোনো অতিরিক্ত গেট টাইপ লাগে না
একটি একক NAND গেট থেকেই বাকি সব মৌলিক গেট বানানো সম্ভব — এটিই "ইউনিভার্সালিটি"।

৩ · NOR দিয়েও একই কাজ — সংক্ষেপে

NOR গেটও ঠিক একইভাবে ইউনিভার্সাল, শুধু ভূমিকা উল্টে যায় — NOT(A) = NOR(A,A), OR(A,B) = NOT(NOR(A,B)), আর De Morgan's Law-এর অন্য রূপ প্রয়োগ করে AND(A,B) = NOR(NOT A, NOT B)। নীতিটা একেবারে একই — শুধু NAND-এর জায়গায় NOR, আর AND/OR-এর ভূমিকা অদলবদল হয়ে যায়। এই পাঠের কোড সেলে শুধু NAND সংস্করণটি বাস্তবায়ন করা হবে, কারণ প্রমাণের ধরন দুটোতেই অভিন্ন।

৪ · বাস্তব চিপ ম্যানুফ্যাকচারিং-এ কেন গুরুত্বপূর্ণ

একটি বাস্তব ইঞ্জিনিয়ারিং সিদ্ধান্ত

একটি চিপ ফ্যাক্টরিতে AND, OR, NOT, XOR — প্রতিটির জন্য আলাদা আলাদা ফিজিক্যাল ট্রানজিস্টর-লেআউট ডিজাইন, টেস্ট ও মাস-প্রোডিউস করার চেয়ে, শুধু একটিমাত্র ইউনিফর্ম বিল্ডিং ব্লক (সাধারণত NAND) বারবার পুনরাবৃত্তি করে বসানো অনেক সস্তা, সহজ ও নির্ভরযোগ্য — এটি নিছক তাত্ত্বিক সৌন্দর্য নয়, বাস্তব সেমিকন্ডাক্টর ম্যানুফ্যাকচারিং-এর একটি সরাসরি ব্যবহারিক কারণ।

নিচের কোড সেলে শুধুমাত্র NAND(a, b) ফাংশনটি বানানো হবে — তারপর NOT, AND, OR — এই তিনটি গেটই শুধুমাত্র NAND-কে কল করে বানানো হবে (Python-এর সরাসরি &/|/not ব্যবহার না করে), এবং প্রতিটির পূর্ণ ট্রুথ টেবিল প্রত্যাশিত ফলাফলের সাথে মিলিয়ে যাচাই করা হবে।

Python
# শুধু NAND -- একমাত্র প্রিমিটিভ গেট হিসেবে ধরে নেওয়া হলো
def NAND(a, b):
    """মৌলিক দেওয়া গেট -- বাস্তব হার্ডওয়্যারে প্রায়ই এটিই একমাত্র ফিজিক্যাল বিল্ডিং ব্লক"""
    if a == 1 and b == 1:
        return 0
    return 1

# --- নিচের তিনটি গেট শুধুই NAND-কে কল করে বানানো, সরাসরি &/|/not ব্যবহার নেই ---

def NOT(a):
    return NAND(a, a)

def AND(a, b):
    n = NAND(a, b)
    return NAND(n, n)

def OR(a, b):
    return NAND(NOT(a), NOT(b))

print("NAND-এর নিজের ট্রুথ টেবিল")
for a in (0, 1):
    for b in (0, 1):
        print(f"  NAND({a},{b}) = {NAND(a, b)}")

print()
print("NAND দিয়ে বানানো NOT-এর ট্রুথ টেবিল")
for a in (0, 1):
    print(f"  NOT({a}) = {NOT(a)}")

print()
print("NAND দিয়ে বানানো AND-এর ট্রুথ টেবিল")
and_table = {}
for a in (0, 1):
    for b in (0, 1):
        and_table[f"{a}{b}"] = AND(a, b)
        print(f"  AND({a},{b}) = {AND(a, b)}")

print()
print("NAND দিয়ে বানানো OR-এর ট্রুথ টেবিল")
or_table = {}
for a in (0, 1):
    for b in (0, 1):
        or_table[f"{a}{b}"] = OR(a, b)
        print(f"  OR({a},{b}) = {OR(a, b)}")

expected_and = {"00": 0, "01": 0, "10": 0, "11": 1}
expected_or  = {"00": 0, "01": 1, "10": 1, "11": 1}

print()
print("প্রত্যাশিত AND টেবিল:", expected_and)
print("আমাদের AND টেবিল:   ", and_table)
print("মিলেছে কি?", and_table == expected_and)

print()
print("প্রত্যাশিত OR টেবিল:", expected_or)
print("আমাদের OR টেবিল:   ", or_table)
print("মিলেছে কি?", or_table == expected_or)

    
লক্ষ্য করুন — পুরো কোডে কোথাও সরাসরি Python-এর &, |, বা not ব্যবহার হয়নি; শুধুমাত্র NAND ফাংশনের বারবার কল দিয়েই NOT, AND, OR — প্রতিটির ট্রুথ টেবিল প্রত্যাশিত ফলাফলের সাথে হুবহু মিলে গেছে। এটিই কোড-ভেরিফাইড প্রমাণ যে NAND সত্যিই ইউনিভার্সাল।
মূল কথা · Key takeaway

NAND (এবং একইভাবে NOR) দিয়ে একাই যেকোনো বুলিয়ান ফাংশন বানানো সম্ভব — এই একটি বৈশিষ্ট্যই বাস্তব চিপ ডিজাইনে NAND-কে সবচেয়ে বহুল ব্যবহৃত বিল্ডিং ব্লকে পরিণত করেছে। M2-এ (L08 থেকে) এখন এই মৌলিক গেটগুলো দিয়েই প্রথম বাস্তব "দরকারি" সার্কিট — অ্যাডার — বানানো শুরু হবে।

ভাবনার প্রশ্ন

প্রতিটি প্রশ্ন নিজে কিছুক্ষণ ভাবুন — তারপর "→ উত্তর" চাপুন।

প্র ০১ শুধু AND, OR, NOT গেট দিয়ে কি একইভাবে "ইউনিভার্সাল" দাবি করা যায়? কেন যায় না?

না। AND, OR, NOT — এই তিনটি একসাথে থাকলে সব বুলিয়ান ফাংশন বানানো যায়, কিন্তু এককভাবে কোনোটিই একা যথেষ্ট নয় — যেমন শুধু AND গেট (যতগুলো ইচ্ছা, যেকোনো ইনপুট কম্বিনেশনে) দিয়ে কখনোই NOT বানানো যায় না, কারণ AND-এর আউটপুট কখনো তার ইনপুটের চেয়ে "বেশি ১" হতে পারে না। ইউনিভার্সাল গেটের সংজ্ঞা হলো একটি একক গেট টাইপ যথেষ্ট — NAND/NOR এই কঠিন শর্তটি পূরণ করে, AND/OR/NOT এককভাবে করে না।

প্র ০২ AND(A,B) = NOT(NAND(A,B)) সূত্রে "NOT-এর NOT" যুক্তিটা ঠিক কীভাবে কাজ করে?

NAND মানে "NOT-AND" — অর্থাৎ NAND(A,B) আসলে AND(A,B)-এর বিপরীত ফলাফল দেয়। তাহলে সেই ফলাফলের উপর আবার একটি NOT (যেটি নিজেই NAND(x,x) দিয়ে বানানো) প্রয়োগ করলে, দুটো ইনভার্সন একে অপরকে কাটিয়ে দেয় — NOT(NOT(AND(A,B))) = AND(A,B)। এটিই বীজগণিতের ডাবল-নেগেশন নিয়মের (¬¬X = X) সরাসরি প্রয়োগ, শুধু গেটের ভাষায়।

প্র ০৩ বাস্তব জীবনে যদি NAND-ই সবচেয়ে সস্তা হয়, তাহলে চিপে কেন XOR-এর মতো অন্য গেটও দেখা যায়?

তাত্ত্বিকভাবে NAND দিয়েই XOR বানানো সম্ভব (কয়েকটি NAND-এর সমন্বয়ে), কিন্তু ব্যবহারিকভাবে যদি কোনো সার্কিটে XOR অনেকবার লাগে (যেমন অ্যাডারে), তখন একটি সরাসরি অপ্টিমাইজড XOR-লেআউট ব্যবহার করলে কম ট্রানজিস্টর ও কম বিলম্বে (delay) একই কাজ হয় — তাই বাস্তব চিপে প্রায়ই NAND-ভিত্তিক ইউনিফর্মিটির সাথে পারফরম্যান্সের জন্য কিছু বিশেষায়িত গেটও মিশিয়ে ব্যবহার করা হয়। "ইউনিভার্সাল" মানে "সম্ভব," সবসময় "সবচেয়ে দক্ষ" নয়।

অনুশীলন

  1. হাতে বসিয়ে দেখুন: A=1, B=0 এর জন্য OR(A,B) = NAND(NOT(A), NOT(B)) সূত্রটি ধাপে ধাপে হাতে-কলমে গণনা করে দেখান যে ফলাফল 1 আসে।

    NOT(A) = NOT(1) = 0। NOT(B) = NOT(0) = 1। এখন NAND(0, 1) — যেহেতু দুটো ইনপুট একসাথে 1 নয় (একটি 0, একটি 1), NAND-এর সংজ্ঞা অনুযায়ী ফলাফল 1। তাই OR(1,0) = NAND(NOT(1), NOT(0)) = NAND(0,1) = 1 — যা প্রত্যাশিত OR(1,0)=1-এর সাথে হুবহু মেলে।

  2. চিন্তা করুন: উপরের কোডে OR ফাংশনটি শুধু NOR দিয়ে বানাতে হলে (NAND নয়) সূত্রটা কেমন হবে (এখনো কোড পরিবর্তন করবেন না)?

    NOR দিয়ে OR বানানো সবচেয়ে সহজ ধাপ — যেহেতু NOR মানেই "NOT-OR," তাই তার উপর আরেকটি NOT (যা NOR(x,x) দিয়ে বানানো) প্রয়োগ করলেই বিশুদ্ধ OR পাওয়া যায়: OR(A,B) = NOT(NOR(A,B)) = NOR(NOR(A,B), NOR(A,B)) — ঠিক একই "ডাবল-নেগেশন" নীতি, শুধু NAND-এর জায়গায় NOR বসিয়ে এবং AND/OR-এর ভূমিকা অদলবদল করে।

আরও পড়ুন · ABCL TECH-এ আপনার পরবর্তী পদক্ষেপ

  • কোর্সের সম্পূর্ণ সিলেবাস দেখুন ৫৭টি পাঠ M1 শেষ হলো — এরপর M2-তে অ্যাডার, মাল্টিপ্লেক্সার, ডিকোডারের মতো বাস্তব কম্বিনেশনাল সার্কিট শুরু হবে।
  • আগের পাঠ L06 কারনো ম্যাপ (K-Map) সিমপ্লিফিকেশন — এই পাঠের ইউনিভার্সাল-গেট প্রমাণেও একই "truth-table মিলিয়ে যাচাই" নীতি ব্যবহৃত হয়েছে।
  • পরের পাঠ L08 হাফ অ্যাডার ও ফুল অ্যাডার — মৌলিক গেট দিয়ে বানানো প্রথম বাস্তব "দরকারি" সার্কিট, যা সংখ্যা যোগ করতে পারে।
আগের পাঠ
কারনো ম্যাপ (K-Map) সিমপ্লিফিকেশন