অ্যারে এবং ডেটা স্ট্রাকচার (The Deep Dive)
অন্যান্য প্রোগ্রামিং ল্যাঙ্গুয়েজে (যেমন C, Java) অ্যারে, লিস্ট, ম্যাপ, ডিকশনারি—সব আলাদা। কিন্তু পিএইচপি-তে সব এক! পিএইচপি অ্যারে হলো একটি Universal Data Structure।
একজন জুনিয়র ডেভেলপার অ্যারে ব্যবহার করে ডেটা রাখতে। একজন Senior Developer অ্যারে ব্যবহার করার সময় চিন্তা করে Hashtable Collision, Memory Bucket, এবং Iteration Cost নিয়ে।
৪.১ পিএইচপি অ্যারে ইন্টারনালস: হ্যাশটেবল আর্কিটেকচার
পিএইচপি অ্যারে মেমোরিতে Contiguous (পরপর সাজানো) নয়। এটি আসলে একটি Ordered Map বা হাইব্রিড Hashtable।
🔬 মেমোরিতে এটি কীভাবে থাকে? (The Bucket System)
যখন আপনি $arr['name'] = 'Shagor' লেখেন, তখন ভেতরে ৪টি ঘটনা ঘটে:
- Hashing: পিএইচপি প্রথমে 'name'-কে একটি হ্যাশ ফাংশনের মাধ্যমে ইন্টিজারে রূপান্তর করে (যেমন: 18376218)
- Indexing: এই হ্যাশ ইন্টিজার দিয়ে একটি ইন্ডেক্স তৈরি হয়
- Bucket: সেই ইন্ডেক্সে একটি Bucket তৈরি হয়
- Zval: সেই বাকেটের ভেতর ভ্যালু ('Shagor') স্টোর হয়
🏗️ স্ট্রাকচারাল ভিউ:
Array Data Structure
├── Bucket 1 [Key: 0, Value: "First", Next: Bucket 2]
├── Bucket 2 [Key: "name", Value: "Shagor", Next: Bucket 3]
└── Bucket 3 [Key: 5, Value: true, Next: null]
এই কারণেই পিএইচপি অ্যারেতে একই সাথে Index (0, 1) এবং Key ("name") রাখা যায়। পিএইচপির কাছে দুটোই হ্যাশটেবল এন্ট্রি মাত্র।
৪.২ অ্যাডভান্সড অ্যারে ফাংশন ও পারফরম্যান্স (Senior Analysis)
জুনিয়ররা কোড ছোট করতে array_map পছন্দ করে, সিনিয়রা পারফরম্যান্স বাঁচাতে foreach পছন্দ করে। কেন?
❌ ১. array_map কেন স্লো?
// ❌ Slower for huge data
$res = array_map(fn($x) => $x * 2, $arr);
- এটি প্রতি এলিমেন্টের জন্য একবার করে ফাংশন কল করে (Function Call Overhead)
- এটি সম্পূর্ণ নতুন একটি অ্যারে রিটার্ন করে (Double Memory Usage)
✅ Senior Alternative:
foreach ($arr as &$v) {
$v *= 2;
}
unset($v); // Reference break করা বাধ্যতামূলক
এটি মেমোরিতে নতুন অ্যারে না বানিয়েই কাজ সারে।
⚠️ ২. array_filter এর মেমোরি ফাঁদ
$arr = [0 => 'a', 1 => 'b', 2 => 'c'];
$res = array_filter($arr, fn($v) => $v !== 'b');
আউটপুট কী হবে? [0 => 'a', 2 => 'c'] (খেয়াল করুন ইনডেক্স ১ নেই)
array_filter মূল কি (Key) প্রিজার্ভ করে। আপনি যদি json_encode করেন, এটি আর অ্যারে থাকবে না, অবজেক্ট হয়ে যাবে ({"0":"a", "2":"c"})।
⚡ ৩. array_merge বনাম + অপারেটর (The Interview Favorite)
এটি না জানলে বাগ ফিক্স করা অসম্ভব।
| Feature | array_merge($a, $b) | $a + $b |
|---|---|---|
| Numeric Keys | Renumber করে (0, 1, 2...) | Preserve করে (ডুপ্লিকেট হলে বামেরটা রাখে) |
| String Keys | শেষেরটা আগেরটাকে Override করে | বামেরটা (First one) জয়ী হয়, ডানেরটা ইগনোর করে |
$a = [1 => "One"];
$b = [1 => "Two"];
print_r(array_merge($a, $b)); // [0 => "One", 1 => "Two"] (Renumbered)
print_r($a + $b); // [1 => "One"] ($b ignored collision)
৪.৩ সর্টিং পিটফলস (The Dangerous Zone)
পিএইচপি-তে অ্যারে সর্ট করা মানে মেমোরির ওপর অত্যাচার করা।
🔄 প্রসেস: Copy Array → Calculate Hash → Move Buckets → Re-index
✅ ফাংশন সিলেকশন গাইড
sort(): শুধু ভ্যালু সর্ট করে, কিন্তু Keys হারিয়ে ফেলেasort(): ভ্যালু সর্ট করে কিন্তু Keys ঠিক রাখে (Associative array-র জন্য best)ksort(): Key অনুযায়ী সর্ট করে
❌ usort কেন এড়িয়ে চলবেন?
usort($largeArray, function($a, $b) {
return $a <=> $b;
});
বড় অ্যারেতে এটি অত্যন্ত ধীরগতির। কারণ প্রতিবার কম্পেয়ার করতে তাকে পিএইচপি ফাংশন কল করতে হয়। যদি সম্ভব হয়, ডাটাবেস লেভেল (SQL ORDER BY) থেকেই সর্ট করে আনুন।
৪.৪ SPL ডেটা স্ট্রাকচার (সুপার পারফরম্যান্স)
পিএইচপির সাধারণ অ্যারে "Jack of all trades, master of none"। স্পেশাল কাজের জন্য পিএইচপির স্ট্যান্ডার্ড লাইব্রেরি (SPL) ব্যবহার করুন যা C লেভেলে অপ্টিমাইজড।
🚀 ১. SplFixedArray (রকেট স্পিড)
সাধারণ অ্যারে ডাইনামিক, মেমোরি এলোমেলো। SplFixedArray ফিক্সড সাইজ নেয়, তাই এটি C Array-এর মতো ফাস্ট।
$arr = new SplFixedArray(10000);
$arr[0] = "Fast";
// সাধারণ অ্যারের চেয়ে ৩০-৪০% মেমোরি কম খায়।
📋 ২. SplStack এবং SplQueue
সাধারণ অ্যারে দিয়ে স্ট্যাক বানালে (array_push/pop), পিএইচপিকে প্রতিবার হ্যাশ ইনডেক্স রি-ক্যালকুলেট করতে হয়। SPL দিয়ে করলে তা হয় না।
// ✅ Queue (FIFO)
$q = new SplQueue();
$q->enqueue("Task 1");
$q->enqueue("Task 2");
echo $q->dequeue(); // Task 1
// ✅ Stack (LIFO)
$s = new SplStack();
$s->push("Page 1");
echo $s->pop(); // Page 1
📦 ৩. ArrayObject
এটি অ্যারে-কে অবজেক্ট হিসেবে ব্যবহারের সুবিধা দেয়। তবে মনে রাখবেন, এটি সাধারণ অ্যারের চেয়ে দ্রুত নয়, কিন্তু এটি OOP স্টাইলে কাজ করার সুবিধা দেয়।
৪.৫ অ্যারে বনাম JSON পারফরম্যান্স
অনেক ডেভেলপার ডেটা স্টোর করতে বা পাস করতে অকারণে JSON ব্যবহার করেন।
⚡ Array Access
O(1)
সুপার ফাস্ট
🐌 JSON Encode/Decode
O(N)
স্লো এবং CPU হেভি
🔍 কেন JSON স্লো?
- হ্যাশটেবল থেকে স্ট্রিং কনভারশন
- UTF-8 এনকোডিং চেক
- স্পেশাল ক্যারেক্টার এস্কেপিং
💡 Senior Rule:
শুধুমাত্র ক্লায়েন্ট (Browser/API) কে রেসপন্স পাঠানোর মুহূর্তেই json_encode ব্যবহার করুন। ইন্টারনাল প্রসেসিংয়ের জন্য সবসময় অ্যারে বা অবজেক্ট ব্যবহার করুন।
🎯 Senior Developer Interview Questions (Chapter 4)
Q: array_merge এবং + অপারেটরের মধ্যে মেমোরি এবং লজিক্যাল পার্থক্য কী?
array_merge নিউমারিক কি (Key) রি-ইনডেক্স করে এবং স্ট্রিং কি-তে ভ্যালু ওভাররাইড করে। + অপারেটর ইনডেক্স প্রিজার্ভ করে এবং ডুপ্লিকেট কি থাকলে প্রথম অ্যারেকে প্রায়োরিটি দেয়।
Q: পিএইচপি অ্যারে আসলে কী ধরনের ডেটা স্ট্রাকচার?
এটি একটি Ordered Map। এটি হ্যাশটেবল এবং ডাবলি লিংকড লিস্টের (Doubly Linked List) সমন্বয়ে তৈরি।
Q: ১ মিলিয়ন ডেটার অ্যারেতে array_map ব্যবহার করা কেন উচিত নয়? বিকল্প কী?
array_map নতুন অ্যারে তৈরি করে মেমোরি ডাবল করে ফেলে এবং ফাংশন কলের ওভারহেড থাকে। বিকল্প হিসেবে foreach লুপ এবং রেফারেন্স (&) ব্যবহার করা মেমোরি এফিশিয়েন্ট।
Q: SplFixedArray কখন এবং কেন ব্যবহার করবেন?
যখন অ্যারের সাইজ আগে থেকেই জানা থাকে এবং ইনডেক্স হবে ইন্টিজার। এটি সাধারণ অ্যারের চেয়ে দ্রুত এবং কম মেমোরি খরচ করে কারণ এতে হ্যাশটেবল ওভারহেড নেই।
🎯 অধ্যায় ৪ এর সারাংশ (Summary)
এই অধ্যায়ে আমরা শিখলাম:
- ✓Array Internals: Hashtable + Doubly Linked List (Ordered Map)
- ✓Performance: array_map vs foreach (reference) - মেমোরি ডাবল হয়
- ✓array_merge vs +: Renumber vs Preserve keys
- ✓Sorting: sort() destroys keys, asort() preserves, usort() slow
- ✓SPL: SplFixedArray (30-40% memory less), SplQueue, SplStack
- ✓Array vs JSON: শুধু API response-এ JSON, internally array ব্যবহার করুন
✨ পরবর্তী অধ্যায়: Part 5 - Strings & Regular Expressions — যেখানে UTF-8 ট্র্যাপ এবং Regex পারফরম্যান্স দেখব।
প্রস্তুত তো? 🚀