ডাটাবেসের ডেটা বিশ্লেষণের অন্যতম শক্তিশালী উপায় হলো গ্রুপিং – অর্থাৎ, কোনো একটি কলামের ভিত্তিতে সারিগুলোকে দলবদ্ধ করে প্রতিটি দলের জন্য হিসাব-নিকাশ করা। যেমন, প্রতিটি শহরে কর্মীদের মোট বেতন, অথবা একই নামের কতজন আছে। SQLite-তে এই গ্রুপিং কাজটি করে GROUP BY ক্লজ, যা প্রায় সবসময় অ্যাগ্রিগেট ফাংশন (যেমন SUM, COUNT, AVG, MAX, MIN) এর সাথে ব্যবহৃত হয়। আজকের পর্বে আমরা GROUP BY-এর সিনট্যাক্স, কাজের নিয়ম, বাস্তব উদাহরণ এবং ORDER BY-এর সাথে সমন্বয় বিস্তারিতভাবে শিখব।
পূর্বপ্রস্তুতি
- SQLite ইন্সটল থাকতে হবে (সিরিজের ৩য় পর্ব দেখুন)।
company.dbডাটাবেসেCOMPANYটেবিল থাকতে হবে। আমরা আগের ডেটা রেখে সাথেই নতুন ডুপ্লিকেট রেকর্ড যোগ করব। যদি টেবিল না থাকে, নিচের ধাপে তৈরি করুন:
bash
sqlite3 company.db
sql
CREATE TABLE COMPANY( ID INT PRIMARY KEY NOT NULL, NAME TEXT NOT NULL, AGE INT NOT NULL, ADDRESS CHAR(50), SALARY REAL ); -- প্রাথমিক 7 রেকর্ড INSERT INTO COMPANY VALUES (1, 'Paul', 32, 'California', 20000.00); INSERT INTO COMPANY VALUES (2, 'Allen', 25, 'Texas', 15000.00); INSERT INTO COMPANY VALUES (3, 'Teddy', 23, 'Norway', 20000.00); INSERT INTO COMPANY VALUES (4, 'Mark', 25, 'Rich-Mond', 65000.00); INSERT INTO COMPANY VALUES (5, 'David', 27, 'Texas', 85000.00); INSERT INTO COMPANY VALUES (6, 'Kim', 22, 'South-Hall', 45000.00); INSERT INTO COMPANY VALUES (7, 'James', 24, 'Houston', 10000.00);
- আউটপুট ফরম্যাট:
.header onএবং.mode column।
১. GROUP BY-এর সিনট্যাক্স
GROUP BY ক্লজ SELECT স্টেটমেন্টের WHERE-এর পরে এবং ORDER BY-এর আগে বসে।
sql
SELECT column-list, aggregate_function(column) FROM table_name WHERE condition GROUP BY column1, column2, ... ORDER BY column1, column2, ...;
- column-list: সাধারণত যে কলামের ভিত্তিতে গ্রুপ করবেন, সেই কলাম(গুলো) এখানে দিতে হবে। সাথে অ্যাগ্রিগেট ফাংশনের কলামও থাকে।
- GROUP BY column1, column2: যেসব কলাম অনুসারে দলবদ্ধ করতে চান। একাধিক কলাম ব্যবহার করলে, প্রতিটি অনন্য সমন্বয়ের জন্য আলাদা গ্রুপ হবে।
- ORDER BY: গ্রুপ করার পর ফলাফল সাজাতে ব্যবহার হয়।
২. সহজ উদাহরণ: প্রতিটি কর্মীর মোট বেতন (প্রাথমিক অবস্থা)
প্রাথমিক টেবিলে কোনো ডুপ্লিকেট নাম নেই, তাই GROUP BY NAME করলে প্রতিটি কর্মী আলাদা গ্রুপ, এবং SUM(SALARY) তাদের একক বেতন-ই দেখাবে।
sql
SELECT NAME, SUM(SALARY) FROM COMPANY GROUP BY NAME;
ফলাফল:
text
NAME SUM(SALARY) ---------- ----------- Allen 15000.0 David 85000.0 James 10000.0 Kim 45000.0 Mark 65000.0 Paul 20000.0 Teddy 20000.0
এখানে NAME কলামের প্রতিটি ভিন্ন নাম একটি গ্রুপ। SUM(SALARY) সেই নামের সারির বেতনের যোগফল দেয় (একক সারি বলে বেতনের সমান)।
৩. ডুপ্লিকেট নাম যোগ করে গ্রুপিং এর আসল ক্ষমতা দেখা
বাস্তবে একই নাম একাধিকবার আসতেই পারে। আসুন আমরা আরও তিনটি রেকর্ড যোগ করি যাতে Paul এবং James একাধিকবার থাকে।
sql
INSERT INTO COMPANY VALUES (8, 'Paul', 24, 'Houston', 20000.00); INSERT INTO COMPANY VALUES (9, 'James', 44, 'Norway', 5000.00); INSERT INTO COMPANY VALUES (10, 'James', 45, 'Texas', 5000.00);
এখন টেবিলের অবস্থা:
text
ID NAME AGE ADDRESS SALARY ---------- ---------- ---------- ---------- ---------- 1 Paul 32 California 20000.0 2 Allen 25 Texas 15000.0 3 Teddy 23 Norway 20000.0 4 Mark 25 Rich-Mond 65000.0 5 David 27 Texas 85000.0 6 Kim 22 South-Hall 45000.0 7 James 24 Houston 10000.0 8 Paul 24 Houston 20000.0 9 James 44 Norway 5000.0 10 James 45 Texas 5000.0
এবার আবার NAME দিয়ে গ্রুপ করে বেতনের যোগফল বের করি এবং নামের ক্রমানুসারে সাজাই:
sql
SELECT NAME, SUM(SALARY) AS TOTAL_SALARY FROM COMPANY GROUP BY NAME ORDER BY NAME;
ফলাফল:
text
NAME TOTAL_SALARY ---------- ------------- Allen 15000.0 David 85000.0 James 20000.0 (10000 + 5000 + 5000) Kim 45000.0 Mark 65000.0 Paul 40000.0 (20000 + 20000) Teddy 20000.0
এখানে James-এর মোট বেতন 20,000 এবং Paul-এর 40,000 – দেখাই যাচ্ছে গ্রুপিং-এর জাদু।
৪. অন্যান্য অ্যাগ্রিগেট ফাংশন
GROUP BY-এর সাথে শুধু SUM নয়, আরও ফাংশন ব্যবহার করা যায়:
- COUNT: গ্রুপে কতটি সারি আছে।
- AVG: গড় মান।
- MAX / MIN: সর্বোচ্চ/সর্বনিম্ন মান।
উদাহরণ: প্রতিটি নামের কতজন কর্মী আছে এবং তাদের গড় বয়স:
sql
SELECT NAME, COUNT(*) AS COUNT, AVG(AGE) AS AVG_AGE FROM COMPANY GROUP BY NAME;
ফলাফল:
text
NAME COUNT AVG_AGE ---------- ---------- ---------------- Allen 1 25.0 David 1 27.0 James 3 37.6666666666667 Kim 1 22.0 Mark 1 25.0 Paul 2 28.0 Teddy 1 23.0
৫. GROUP BY-এর সাথে WHERE ও ORDER BY
কোয়েরির ধাপ: WHERE → GROUP BY → ORDER BY → LIMIT।
উদাহরণ: যাদের বেতন ১০,০০০-এর বেশি, সেই সব রেকর্ড NAME দিয়ে গ্রুপ করে মোট বেতন দেখাও, এবং মোট বেতন অনুযায়ী সাজাও (বড় থেকে ছোট)।
sql
SELECT NAME, SUM(SALARY) AS TOTAL FROM COMPANY WHERE SALARY > 10000 GROUP BY NAME ORDER BY TOTAL DESC;
ফলাফল: (যাদের বেতন > 10000, তাদের হিসাব করা হবে। Paul-এর প্রথম রেকর্ড 20000, দ্বিতীয় 20000, James-এর প্রথম 10000টা বাদ, পরের দুইটি 5000 বাদ – তাই James-এর কোনো টোটাল আসবে না, কারণ কোনো SALARY > 10000 নেই। James-এর 10000 রেকর্ডটি condition false, তাই James গ্রুপই তৈরি হবে না। Paul-এর দুইটি রেকর্ডই 20000, তাই TOTAL 40000। David 85000, Kim 45000, Mark 65000, Teddy 20000, Allen 15000। তাই দেখাবে Paul, David, Mark, Kim, Teddy, Allen – James নেই।)
এটি দেখায় WHERE ফিল্টার আগে কাজ করে, তারপর গ্রুপিং।
৬. একাধিক কলাম দিয়ে গ্রুপিং
আপনি চাইলে একাধিক কলামের ভিত্তিতে গ্রুপ করতে পারেন। যেমন প্রতিটি শহরের মধ্যে প্রতিটি নামের কর্মীদের মোট বেতন জানতে:
sql
SELECT ADDRESS, NAME, SUM(SALARY) AS TOTAL FROM COMPANY GROUP BY ADDRESS, NAME;
এটি প্রতিটি (শহর, নাম) সমন্বয়ের জন্য একটি গ্রুপ তৈরি করবে। একই শহরে একই নাম একাধিক বার থাকলে যোগ হবে।
৭. GROUP BY-তে কলাম সিলেক্টের নিয়ম
যে কলামটি GROUP BY-তে দেওয়া হয় না, সেটি সরাসরি SELECT-এ রাখা যাবে না যদি না সেটি কোনো অ্যাগ্রিগেট ফাংশনের ভেতর থাকে। যেমন:
sql
SELECT NAME, AGE FROM COMPANY GROUP BY NAME; -- এরর! কারণ AGE-কে গ্রুপ করা হয়নি
কেন? গ্রুপ করার পর প্রতিটি গ্রুপে একাধিক AGE থাকতে পারে, SQLite জানে না কোন AGE দেখাবে। তবে SQLite নিজস্ব নিয়মে কিছুটা নমনীয়, কিন্তু স্ট্যান্ডার্ড SQL-এ এটি অনুমোদিত নয়। সঠিক উপায়:
sql
SELECT NAME, MAX(AGE) FROM COMPANY GROUP BY NAME; -- ঠিক আছে
অথবা AGE-কে GROUP BY-তে অন্তর্ভুক্ত করতে হবে।
৮. ডিরেক্টরি স্ট্রাকচার ও প্যাকেজ
আমাদের অনুশীলনের জন্য শুধুমাত্র company.db ফাইলটি প্রয়োজন। কোনো অতিরিক্ত প্যাকেজ ইন্সটল করতে হবে না। GROUP BY সম্পূর্ণরূপে SQLite-এর অন্তর্নির্মিত।
৯. গুরুত্বপূর্ণ টিপস
- GROUP BY-তে কলাম নাম্বার ব্যবহার:
GROUP BY 1দিয়ে প্রথম কলামের ভিত্তিতে গ্রুপ করা যায়, কিন্তু স্পষ্টতায় কলাম নাম ব্যবহার করুন। - HAVING ক্লজ: গ্রুপ করার পর শর্ত দিতে
WHEREনা,HAVINGব্যবহার করতে হয়। (পরবর্তী পর্বে আলোচিত হবে।) উদাহরণ:SELECT NAME, SUM(SALARY) FROM COMPANY GROUP BY NAME HAVING SUM(SALARY) > 20000; - NULL মানের আচরণ: GROUP BY NULL-কে একটি আলাদা গ্রুপ হিসেবে গণ্য করে। সব NULL একসাথে একটি গ্রুপে জমা হয়।
- ইনডেক্স: GROUP BY-তে ব্যবহৃত কলামে ইনডেক্স পারফরম্যান্স বাড়ায়।
১০. সম্পূর্ণ অনুশীলন সেশন
টার্মিনালে নিচের ধাপগুলো চালিয়ে দেখুন:
sql
.headers on .mode column -- বর্তমান টেবিল দেখি SELECT * FROM COMPANY; -- নাম অনুসারে মোট বেতন SELECT NAME, SUM(SALARY) FROM COMPANY GROUP BY NAME; -- শহর অনুসারে কর্মী সংখ্যা SELECT ADDRESS, COUNT(*) AS TOTAL_EMP FROM COMPANY GROUP BY ADDRESS; -- বয়স ২৫ এর নিচে, নাম গ্রুপ করে গড় বেতন, সাজানো বেতন অনুযায়ী SELECT NAME, AVG(SALARY) AS AVG_SALARY FROM COMPANY WHERE AGE < 25 GROUP BY NAME ORDER BY AVG_SALARY DESC;
পরবর্তী পর্বে
আমরা শিখব HAVING ক্লজ – GROUP BY-র ফলাফলের উপর শর্ত আরোপ করার কৌশল।
লেখকের কথা: GROUP BY দিয়ে ডেটার গভীরে প্রবেশ করে তথ্যের সারাংশ বের করা সম্ভব। বাংলায় প্রযুক্তি শেখার এই সিরিজে আপনার আগ্রহই আমাদের প্রেরণা। পোস্টটি ভালো লাগলে শেয়ার করতে ভুলবেন না, এবং সম্পূর্ণ সিরিজের আপডেট পেতে ToLearnTeam.com ব্লগ সাবস্ক্রাইব করুন। আপনার মতামত বা প্রশ্ন জানাতে কমেন্ট করুন – আমরা উত্তর দিতে প্রস্তুত!
SQLite Full Course
- SQLite পরিচিতি ও ইন্সটলেশন গাইড – বাংলায় প্রথম ডাটাবেস তৈরি
- SQLite কী এবং কেন শিখবেন? সম্পূর্ণ ওভারভিউ ও কমান্ড ক্লাসিফিকেশন (DDL, DML, DQL)
- SQLite ইন্সটলেশন গাইড – Windows, Linux ও Mac-এ ধাপে ধাপে সেটআপ
- SQLite ডট কমান্ড (Dot Commands) – সম্পূর্ণ গাইড, আউটপুট ফরম্যাট ও sqlite_master
- SQLite সিনট্যাক্স (Syntax) – কেস সেনসিটিভিটি, কমেন্ট, সব কমান্ডের গঠন ও উদাহরণ
- SQLite ডেটা টাইপ (Data Type) – স্টোরেজ ক্লাস, টাইপ অ্যাফিনিটি, বুলিয়ান ও ডেট-টাইম
- SQLite ডেটাবেস তৈরি (Create Database) – ধাপে ধাপে গাইড, .dump এক্সপোর্ট ও রিস্টোর
- SQLite ATTACH DATABASE – একাধিক ডাটাবেস সংযুক্ত করার সম্পূর্ণ গাইড (বাংলা)
- SQLite DETACH DATABASE – সংযুক্ত ডাটাবেস বিচ্ছিন্ন করার পূর্ণাঙ্গ গাইড
- SQLite CREATE TABLE স্টেটমেন্ট – টেবিল তৈরি করার পূর্ণাঙ্গ গাইড (বাংলা)
- SQLite DROP TABLE স্টেটমেন্ট – টেবিল ডিলিট করার সম্পূর্ণ গাইড (বাংলা)
- SQLite INSERT INTO স্টেটমেন্ট – ডেটা ইনসার্ট করার সম্পূর্ণ গাইড (বাংলা)
- SQLite SELECT স্টেটমেন্ট – টেবিল থেকে ডেটা ফেচ করার সম্পূর্ণ গাইড (বাংলা)
- SQLite অপারেটর (Operators) – Arithmetic, Comparison, Logical, Bitwise (বাংলা টিউটোরিয়াল)
- SQLite এক্সপ্রেশন (Expressions) – বুলিয়ান, নিউমেরিক ও ডেট এক্সপ্রেশন (বাংলা টিউটোরিয়াল)
- SQLite AND ও OR অপারেটর – একাধিক শর্ত দিয়ে ডেটা ফিল্টার (বাংলা টিউটোরিয়াল)
- SQLite UPDATE Query – টেবিলের ডেটা পরিবর্তন করার সম্পূর্ণ গাইড (বাংলা)
- SQLite DELETE Query – টেবিল থেকে ডেটা মুছে ফেলার সম্পূর্ণ গাইড (বাংলা)
- SQLite LIKE Operator – প্যাটার্ন মিলিয়ে ডেটা খোঁজার সম্পূর্ণ গাইড (বাংলা)
- SQLite GLOB Operator – কেস-সেনসিটিভ প্যাটার্ন মিলিয়ে ডেটা খোঁজা (বাংলা)
- SQLite LIMIT Clause – ডেটা সীমিত করে আনার সম্পূর্ণ গাইড (বাংলা)
- SQLite ORDER BY ক্লজ – ডেটা সাজানোর সম্পূর্ণ গাইড (বাংলা)
- SQLite GROUP BY ক্লজ – ডেটা গ্রুপ করে বিশ্লেষণ করার সম্পূর্ণ গাইড (বাংলা)
- SQLite HAVING ক্লজ – গ্রুপের উপর শর্ত দিয়ে ডেটা ফিল্টার (বাংলা টিউটোরিয়াল)
- SQLite DISTINCT Keyword – ডুপ্লিকেট ডেটা বাদ দিয়ে ইউনিক ভ্যালু পাওয়া (বাংলা)
- SQLite PRAGMA কমান্ড – ডাটাবেস কনফিগারেশন ও সেটিংস (বাংলা টিউটোরিয়াল)
- SQLite Constraints – NOT NULL, DEFAULT, UNIQUE, PRIMARY KEY, CHECK (বাংলা টিউটোরিয়াল)
- SQLite JOINS – CROSS JOIN, INNER JOIN, LEFT OUTER JOIN (বাংলা টিউটোরিয়াল)
- SQLite UNION ও UNION ALL – একাধিক SELECT একত্রিত করার সম্পূর্ণ গাইড (বাংলা)
- SQLite NULL Values – NULL কী, IS NULL, IS NOT NULL (বাংলা টিউটোরিয়াল)
- SQLite ALIAS Syntax – টেবিল ও কলামের অস্থায়ী নাম (বাংলা টিউটোরিয়াল)
- SQLite Triggers – স্বয়ংক্রিয় ট্রিগার তৈরি, ব্যবহার ও মুছে ফেলা (বাংলা টিউটোরিয়াল)
- SQLite Indexes – CREATE, UNIQUE, COMPOSITE, DROP INDEX (বাংলা টিউটোরিয়াল)
- SQLite INDEXED BY Clause – নির্দিষ্ট ইনডেক্স ব্যবহার ও NOT INDEXED (বাংলা)
- SQLite ALTER TABLE Command – টেবিলের গঠন পরিবর্তন (বাংলা টিউটোরিয়াল)
- SQLite TRUNCATE TABLE Command – DELETE ও DROP দিয়ে টেবিল খালি করা (বাংলা)
- SQLite Views – ভার্চুয়াল টেবিল তৈরি, ব্যবহার ও ডিলিট (বাংলা টিউটোরিয়াল)
- SQLite Transactions – BEGIN, COMMIT, ROLLBACK ও ACID প্রপার্টি (বাংলা)
- SQLite Subqueries – SELECT, INSERT, UPDATE, DELETE-এ সাবকোয়েরি ব্যবহার (বাংলা টিউটোরিয়াল)
- SQLite AUTOINCREMENT – স্বয়ংক্রিয়ভাবে প্রাইমারি কি মান বৃদ্ধি (বাংলা টিউটোরিয়াল)
- SQLite SQL Injection – কী, কেন বিপজ্জনক ও প্রতিরোধের উপায় (বাংলা টিউটোরিয়াল)
- SQLite EXPLAIN ও EXPLAIN QUERY PLAN – কোয়েরি বিশ্লেষণ (বাংলা টিউটোরিয়াল)
- SQLite VACUUM – ডাটাবেস পরিষ্কার, স্পেস রিক্লেইম ও অটো-ভ্যাকুয়াম (বাংলা টিউটোরিয়াল)
- SQLite Date & Time ফাংশন – date(), time(), datetime(), julianday(), strftime() (বাংলা টিউটোরিয়াল)
- SQLite Useful Functions – COUNT, MAX, MIN, AVG, SUM, RANDOM, ABS, UPPER, LOWER, LENGTH (বাংলা টিউটোরিয়াল)
- SQLite C/C++ প্রোগ্রামিং – sqlite3_open, exec, close, callback (বাংলা টিউটোরিয়াল)
- SQLite PHP প্রোগ্রামিং – PHP-তে SQLite ডাটাবেস ব্যবহার (বাংলা টিউটোরিয়াল)
- SQLite Perl প্রোগ্রামিং – DBI/DBD::SQLite দিয়ে ডাটাবেস অপারেশন (বাংলা)
- SQLite Python প্রোগ্রামিং – sqlite3 মডিউল দিয়ে CRUD অপারেশন (বাংলা টিউটোরিয়াল)
- SQLite Quick Guide – বাংলায় পূর্ণাঙ্গ সংক্ষিপ্ত টিউটোরিয়াল (শেখার সহজ গাইড)
