কী-ভ্যালু স্টোরেজ
এই পাঠে যা শিখবেন
- কী-ভ্যালু স্টোরেজ কী এবং কখন এটি ব্যবহার করা উচিত (ছোট, সমতল, স্ট্রাকচারবিহীন ডেটার জন্য)
get/set/remove— এই তিনটি অপারেশনের সঠিক আচরণ- একটি মিসিং কী-এর জন্য ডিফল্ট-ভ্যালু ফলব্যাক কেন গুরুত্বপূর্ণ
- একটি সত্যিকারের, কার্যকর
KeyValueStoreক্লাস — এবং কেন এই ইন-মেমোরি সংস্করণ বাস্তব ডিভাইসের পার্সিস্টেন্স প্রতিস্থাপন করতে পারে না
১ · কী-ভ্যালু স্টোরেজ কী
কী-ভ্যালু স্টোরেজKey-Value Storageডেটাকে নাম (কী) ও মান (ভ্যালু) জোড়া হিসেবে সংরক্ষণ করার সবচেয়ে সরল পার্সিস্টেন্স মডেল — কোনো টেবিল, কলাম বা রিলেশন নেই, শুধু একটি ফ্ল্যাট ম্যাপিং। মোবাইল অ্যাপে এটি সাধারণত ছোট, সমতল ডেটার জন্য ব্যবহৃত হয় — ইউজারের থিম পছন্দ, ফন্ট সাইজ, "অনবোর্ডিং দেখা হয়েছে কি না" এই ধরনের ফ্ল্যাগ, বা কোনো ফিচার-ফ্ল্যাগের মান। এটি L33-এ শেখা লোকাল SQL ডেটাবেসের মতো জটিল কোয়েরি বা একাধিক টেবিলের মধ্যে সম্পর্ক ধরে রাখতে পারে না — এবং সেটাই এর উদ্দেশ্যও নয়।
অ্যাপ-স্কোপড একটি প্লিস্ট-ব্যাকড কী-ভ্যালু স্টোর, ছোট সেটিংসের জন্য অফিসিয়ালি সুপারিশকৃত।
একটি XML ফাইলে ব্যাক-আপ করা কী-ভ্যালু স্টোর, প্রতিটি অ্যাপের নিজস্ব প্রাইভেট স্টোরেজে থাকে।
একটি অ্যাসিঙ্ক্রোনাস, আনএনক্রিপ্টেড কী-ভ্যালু স্টোর — নিচে প্ল্যাটফর্ম-নির্দিষ্ট মেকানিজম ব্যবহার করে।
২ · get / set / remove — তিনটি অপারেশন
যেকোনো কী-ভ্যালু স্টোরের ইন্টারফেস তিনটি অপারেশনে ফিট করে যায়। set(key, value) একটি
মান সংরক্ষণ করে (আগে থেকে থাকলে ওভাররাইট করে)। get(key, default) মান ফিরিয়ে দেয় — কিন্তু
কী-টি না থাকলে ক্র্যাশ না করে default প্যারামিটারে দেওয়া মান ফিরিয়ে দেয়, যা এই প্যাটার্নের
সবচেয়ে গুরুত্বপূর্ণ নিরাপত্তা বৈশিষ্ট্য। remove(key) একটি কী মুছে দেয়, না থাকলে নিরাপদে
কিছুই করে না।
# একটি সত্যিকারের কী-ভ্যালু স্টোর -- একটি dict-এর উপর get/set/remove
# একটি বাস্তব ডিভাইসে এই dict-টি ডিস্কে (UserDefaults/SharedPreferences) লেখা হতো,
# যাতে অ্যাপ রিস্টার্টের পরও ডেটা টিকে থাকে -- এই in-memory সংস্করণ শুধু আচরণটি সিমুলেট করে
class KeyValueStore:
def __init__(self):
self._data = {}
def set(self, key, value):
self._data[key] = value
print(f"SET {key!r} = {value!r}")
def get(self, key, default=None):
found = key in self._data
value = self._data.get(key, default)
status = "পাওয়া গেছে" if found else "পাওয়া যায়নি -- ডিফল্ট ব্যবহার হলো"
print(f"GET {key!r} -> {value!r} ({status})")
return value
def remove(self, key):
existed = key in self._data
if existed:
del self._data[key]
status = "মুছে ফেলা হলো" if existed else "ছিলোই না, কিছু করা হয়নি"
print(f"REMOVE {key!r} ({status})")
store = KeyValueStore()
store.set("theme", "dark")
store.set("font_size", 16)
store.set("onboarding_seen", True)
store.get("theme")
store.get("font_size")
store.get("notifications_enabled", default=True) # এই কী কখনো set হয়নি
store.remove("onboarding_seen")
store.get("onboarding_seen", default=False) # সরানোর পর আবার -- এখন মিসিং
print(f"\nবর্তমান সব সংরক্ষিত ডেটা: {store._data}")
notifications_enabled কী-টি কখনো set করা হয়নি, তাই
get এটি খুঁজে না পেয়ে সরাসরি default=True মানটি ফিরিয়ে দেয় — কোনো
KeyError ছাড়াই। এই ফলব্যাক আচরণ ছাড়া প্রতিটি get কলের আগে
"কী-টি আদৌ আছে কি না" আলাদাভাবে চেক করতে হতো, যা বাস্তব কোডে বিরক্তিকর ও ভুলপ্রবণ।
একটি বাস্তব ডিভাইসে এই _data ডিকশনারিটি প্রতিটি set-এর
পর (বা নির্দিষ্ট বিরতিতে) ডিস্কে ফ্লাশ হয়ে যায়, তাই অ্যাপ সম্পূর্ণ বন্ধ (killed) হয়ে আবার চালু হলেও
মানগুলো টিকে থাকে — এই Pyodide স্যান্ডবক্সে প্রতিটি কোড-সেল রান একটি তাজা Python পরিবেশে চলে বলে
এই ইন-মেমোরি dict নিজে থেকে সেই "রিস্টার্টের পরও টেকা" ব্যাপারটি প্রমাণ করতে পারে না — L31-এ আমরা
সেই CONCEPT-টি একটি স্পষ্ট background→killed→relaunch সিমুলেশন দিয়ে আলাদাভাবে দেখিয়েছিলাম।
কী-ভ্যালু স্টোরেজ হলো "সবচেয়ে সরল যা কাজ করে" নীতির একটি প্র্যাকটিক্যাল উদাহরণ — এটি কোনো কোয়েরি ইঞ্জিন বা স্কিমা অফার করে না, কিন্তু ছোট, স্বাধীন সেটিংসের জন্য এটিই সবচেয়ে দ্রুত ও সহজ সমাধান। যখন ডেটার মধ্যে সম্পর্ক থাকে বা ফিল্টার/সর্ট করে কোয়েরি করার দরকার হয়, তখন পরের পাঠে (L33) আমরা একধাপ উপরে উঠে লোকাল SQL-স্টাইল ডেটাবেসে যাব।
ভাবনার প্রশ্ন
প্রতিটি প্রশ্ন নিজে কিছুক্ষণ ভাবুন — তারপর "→ উত্তর" চাপুন।
প্র ০১
get মেথডে default প্যারামিটার না থাকলে কী সমস্যা হতো?
তখন প্রতিটি কল-সাইটে আগে থেকে if key in store._data: দিয়ে চেক করতে হতো, নয়তো
একটি মিসিং কী-এর জন্য KeyError (বা None ফেরত পেয়ে পরবর্তী কোডে
অপ্রত্যাশিতভাবে ভেঙে পড়া) হতো। ডিফল্ট-ভ্যালু ফলব্যাক এই চেকটিকে get-এর ভেতরেই
একবার লিখে সবার জন্য সমাধান করে দেয়।
প্র ০২ কী-ভ্যালু স্টোরেজ দিয়ে কেন একাধিক সম্পর্কিত রেকর্ড (যেমন ১০০টি নোট) ভালোভাবে সংরক্ষণ করা যায় না?
কী-ভ্যালু স্টোরে কোনো "একাধিক রেকর্ডে ফিল্টার করো" বা "নির্দিষ্ট শর্তে সাজাও" ধরনের কোয়েরি নেই — প্রতিটি কী স্বাধীন। ১০০টি নোট রাখতে হলে ১০০টি আলাদা কী দরকার হতো, আর "শুধু পিন করা নোটগুলো দেখাও" জিজ্ঞেস করতে সবগুলো কী নিজে হাতে লুপ করে চেক করতে হতো — এটাই ঠিক সেই সমস্যা যা L33-এর লোকাল SQL-স্টাইল টেবিল সমাধান করে।
প্র ০৩
কোড সেলে remove("onboarding_seen")-এর পর আবার remove("onboarding_seen") কল করলে কী প্রিন্ট হবে?
"REMOVE 'onboarding_seen' (ছিলোই না, কিছু করা হয়নি)" প্রিন্ট হবে — কারণ
existed = key in self._data এখন False হবে (কী-টি প্রথমবারই মুছে
ফেলা হয়েছে), তাই del কল হবে না, শুধু নিরাপদে একটি বার্তা প্রিন্ট হয়ে ফাংশন
রিটার্ন করবে — কোনো এরর ছাড়াই।
অনুশীলন
-
চিন্তা করুন: আপনার ফোনের কোনো অ্যাপের সেটিংস মেনুতে এমন কোনো টগল/স্লাইডার মনে
করুন (যেমন "ডার্ক মোড", "নোটিফিকেশন চালু") যা অ্যাপ বন্ধ করে আবার খুললেও একই অবস্থায় থাকে —
এটি কী-ভ্যালু স্টোরেজের কোন অপারেশনের মাধ্যমে সম্ভব হয় বলে আপনার মনে হয়?
টগল পরিবর্তনের মুহূর্তেই অ্যাপ একটি
set("dark_mode", True)-জাতীয় কল করে সেই মানটি ডিস্কে লিখে ফেলে। অ্যাপ পরের বার চালু হওয়ার সময় UI তৈরি করার আগেই একটিget("dark_mode", default=False)কল করে সংরক্ষিত মানটি পড়ে এবং সেই অনুযায়ী টগলটি সঠিক অবস্থায় দেখায়। -
পরীক্ষা করুন: উপরের কোড সেলে
store.set("font_size", 16)-এর পর একটি নতুন লাইনেstore.set("font_size", 20)যোগ করুন, তারপরstore.get("font_size")কল করে দেখুন কী প্রিন্ট হয়।"GET 'font_size' -> 20 (পাওয়া গেছে)"প্রিন্ট হবে — দ্বিতীয়setকলটি একই কী-এর পুরনো মান (১৬) ওভাররাইট করে ফেলেছে, কারণself._data[key] = valueলাইনটি শর্তহীনভাবে নতুন মান বসিয়ে দেয়। এটাই দেখায় কেনset-কে "insert-or-update" আচরণ বলা হয়, শুধু "insert" নয়।
আরও পড়ুন · ABCL TECH-এ আপনার পরবর্তী পদক্ষেপ
- কোর্সের সম্পূর্ণ সিলেবাস দেখুন ৫৭টি পাঠ অ্যাপ লাইফসাইকেল, মোবাইল UI/UX, MVVM/MVI আর্কিটেকচার, নেভিগেশন, স্টেট ম্যানেজমেন্ট, লোকাল স্টোরেজ, ডিভাইস ফিচার ও ডিপ্লয়মেন্ট — বাকি পাঠগুলো শীঘ্রই যুক্ত হবে।
- পরের পাঠ L33 মোবাইলে লোকাল SQL ডেটাবেস — যখন ডেটার মধ্যে সম্পর্ক ও কোয়েরির দরকার হয়, কী-ভ্যালু স্টোরেজের পরের ধাপ।
- সব Courses দেখুন ABCL TECH C, C++, Python, Java, JavaScript, DSA, DBMS, Discrete Mathematics, System Design, Cybersecurity, Cloud Computing & DevOps, Computer Networks, Operating Systems, Computer Architecture, Programming Languages & Compiler Design, Software Engineering & Git, Theory of Computation, Engineering Economics, Full-Stack Web Frameworks ও Mobile App Development — সব এক জায়গায়।