Skill

Cursors এবং তাদের ব্যবহার

টি-এসকিউএল (T-SQL) - Database Tutorials

400

Cursor T-SQL (Transact-SQL)-এ একটি ডেটাবেস অবজেক্ট যা এক বা একাধিক রেকর্ডে লুপের মাধ্যমে একে একে কাজ করার জন্য ব্যবহৃত হয়। Cursor সাধারণত যখন একটি কুয়েরি থেকে একাধিক রেকর্ড পুনরায় প্রক্রিয়া করতে হয়, তখন ব্যবহার করা হয়। এটি সেই ডেটা একে একে প্রক্রিয়া করার সুযোগ দেয় এবং রেকর্ডে আক্রমণকারী অ্যাকশনগুলো ব্যবহার করতে সাহায্য করে।

ডেটাবেসে Cursor ব্যবহার করা হয় যখন SQL কোডের মধ্যে row-by-row প্রক্রিয়া প্রয়োজন হয়, যা সাধারণ set-based অপারেশনের তুলনায় কিছুটা ধীর গতিতে চলে। তবে, Cursors সাধারণত কম ব্যবহার করা উচিত কারণ এগুলি পারফরম্যান্সের ওপর প্রভাব ফেলতে পারে, বিশেষত বড় ডেটাসেটে।


Cursor এর ধারণা

Cursor একটি পয়েন্টার বা রেফারেন্স যা SQL কুয়েরি থেকে নির্বাচিত রেকর্ডগুলোতে "পয়েন্ট" করে এবং প্রতিটি রেকর্ডে একে একে কাজ করার জন্য ব্যবহৃত হয়। এতে আপনি প্রতিটি রেকর্ডে লুপ চালাতে পারেন, যার মাধ্যমে আপনি INSERT, UPDATE, DELETE, বা অন্য কোনো অপারেশন চালাতে পারেন।


Cursor ব্যবহারের ধাপ

Cursor ব্যবহারের জন্য সাধারণত পাঁচটি মূল ধাপ থাকে:

  1. DECLARE: Cursor তৈরি করা এবং এটি কোন কুয়েরি দ্বারা কাজ করবে তা নির্ধারণ করা।
  2. OPEN: Cursor খুলে ডেটা সেট লোড করা।
  3. FETCH: Cursor থেকে ডেটা সংগ্রহ করা, একে একে রেকর্ডে আক্রমণ করা।
  4. UPDATE/DELETE/INSERT: রেকর্ডে প্রয়োজনীয় পরিবর্তন বা অপারেশন করা।
  5. CLOSE: Cursor বন্ধ করা, যাতে সিস্টেমের রিসোর্স মুক্ত হয়।
  6. DEALLOCATE: Cursor মেমরি থেকে সম্পূর্ণভাবে মুছে ফেলা।

Cursor এর সিনট্যাক্স

DECLARE cursor_name CURSOR FOR
    SELECT column1, column2 FROM table_name WHERE condition;

OPEN cursor_name;

FETCH NEXT FROM cursor_name INTO @var1, @var2; -- রেকর্ডের প্রথম সেট বের করা

WHILE @@FETCH_STATUS = 0
BEGIN
    -- আপনার কাজ করুন, যেমন INSERT, UPDATE, DELETE বা অন্য কোনো অপারেশন
    FETCH NEXT FROM cursor_name INTO @var1, @var2; -- পরবর্তী রেকর্ডে যান
END

CLOSE cursor_name;
DEALLOCATE cursor_name;

Cursor উদাহরণ

ধরা যাক, আপনার একটি Employees টেবিল আছে এবং আপনি প্রতিটি কর্মচারীর বোনাস হিসাব করতে চান। এটি Cursor ব্যবহার করে করা যেতে পারে:

DECLARE @EmployeeID INT, @Salary DECIMAL;

-- Cursor তৈরি
DECLARE employee_cursor CURSOR FOR
    SELECT EmployeeID, Salary FROM Employees WHERE Department = 'Sales';

-- Cursor খোলা
OPEN employee_cursor;

-- প্রথম রেকর্ড FETCH করা
FETCH NEXT FROM employee_cursor INTO @EmployeeID, @Salary;

-- একে একে সব রেকর্ড প্রক্রিয়া করা
WHILE @@FETCH_STATUS = 0
BEGIN
    -- এখানে আপনি কিছু প্রক্রিয়া করতে পারেন, যেমন বোনাস হিসাব
    UPDATE Employees
    SET Salary = @Salary + (@Salary * 0.1) -- 10% বোনাস
    WHERE EmployeeID = @EmployeeID;

    -- পরবর্তী রেকর্ড FETCH করা
    FETCH NEXT FROM employee_cursor INTO @EmployeeID, @Salary;
END

-- Cursor বন্ধ করা
CLOSE employee_cursor;
DEALLOCATE employee_cursor;

এখানে:

  • Cursor employee_cursor তৈরি করা হয়েছে এবং Employees টেবিলের Sales বিভাগের কর্মচারীদের EmployeeID এবং Salary বের করা হচ্ছে।
  • প্রতিটি কর্মচারীর জন্য বোনাস হিসাব করা হচ্ছে এবং তারপর সেই বোনাস যোগ করা হচ্ছে।
  • একবার সমস্ত রেকর্ড প্রক্রিয়া শেষ হলে Cursor বন্ধ করা হচ্ছে।

Cursor এর ধরণ

  1. Static Cursor:
    • এটি একটি স্থির কপি তৈরি করে কুয়েরি থেকে ডেটার এবং যেহেতু এটি স্থির থাকে, এটি ডেটাতে করা কোনো পরিবর্তনকে প্রতিফলিত করে না। এটি সাধারণত সিঙ্গেল ইউজার অ্যাপ্লিকেশনসের জন্য ব্যবহার করা হয়।
  2. Dynamic Cursor:
    • এটি ডেটাবেসে করা কোনো পরিবর্তন (যেমন নতুন রেকর্ড যোগ করা, বর্তমান রেকর্ড পরিবর্তন করা) প্রতিফলিত করে। ডেটার পরিবর্তনগুলিকে লাইভভাবে অনুসরণ করে।
  3. Forward-only Cursor:
    • এটি শুধুমাত্র সামনের দিকে যেতে পারে, অর্থাৎ আপনি একবার রেকর্ডে পৌঁছানোর পরে আবার পেছনে ফিরে যেতে পারবেন না। এটি পারফরম্যান্সের জন্য দ্রুত কিন্তু সীমিত।
  4. Keyset-driven Cursor:
    • এই ধরনের cursor একটি ডেটাসেটের কপি তৈরি করে, তবে ডেটাবেসের বাইরে তৈরি করা পরিবর্তনগুলি এটি প্রতিফলিত করে। তবে, কিছু বিশেষ ক্ষেত্রের পরিবর্তন লক্ষ্য করা যায়।

Cursor ব্যবহার করার সুবিধা এবং অসুবিধা

সুবিধা:

  1. Row-by-row processing: Cursor আপনাকে প্রতিটি রেকর্ডে লুপ চালানোর সুযোগ দেয় এবং আপনার নির্দিষ্ট লজিক প্রয়োগ করতে সাহায্য করে।
  2. ডেটা প্রক্রিয়ার নিয়ন্ত্রণ: আপনি প্রতিটি রেকর্ডে একে একে কাজ করতে পারবেন, যেমন আপডেট বা ডিলিট করা।
  3. Complex operations: যখন সাধারণ SQL query কাজ করতে পারে না, তখন complex লজিক প্রয়োগে সাহায্য করে।

অসুবিধা:

  1. পারফরম্যান্স সমস্যা: Cursor সাধারণত কম পারফরম্যান্স সম্পন্ন হয়, বিশেষত বড় ডেটাসেটে। এটি সার্ভারের মেমরি এবং রিসোর্সের উপর চাপ সৃষ্টি করতে পারে।
  2. Complexity: Cursor কোডকে আরও জটিল করে তোলে এবং কোডের রক্ষণাবেক্ষণ কঠিন হতে পারে।
  3. Locking: Cursor ব্যবহার করার সময় ডেটাবেসে লকিং সমস্যা তৈরি হতে পারে, বিশেষত যদি একটি দীর্ঘ লুপ চলতে থাকে।

Cursor ব্যবহার করা থেকে বিরত থাকার জন্য কিছু বিকল্প

  1. SET-based operations: SQL তে সাধারণত set-based operations (যেমন UPDATE, INSERT, SELECT) ব্যবহার করা হয়, যা একাধিক রেকর্ড প্রক্রিয়া করতে কার্যকরী হয় এবং এর পারফরম্যান্স Cursor এর তুলনায় অনেক ভালো।
  2. CTE (Common Table Expressions): CTE ব্যবহার করে আপনি অনেক সময় row-by-row লজিক এবং জটিল কাজ SET-based পদ্ধতিতে করতে পারেন, যা পারফরম্যান্স উন্নত করে।

সারাংশ

Cursor হলো SQL এর একটি শক্তিশালী টুল যা row-by-row ডেটা প্রক্রিয়া করতে সাহায্য করে। তবে, এটি সাধারণত কম পারফরম্যান্স সম্পন্ন হয় এবং বড় ডেটাসেটে প্রয়োগ করা হলে সিস্টেমের উপর চাপ ফেলতে পারে। তবে, যখন আপনার ডেটাবেসে complex লজিক বা এক্সপ্রেশন প্রয়োগ করার প্রয়োজন হয়, তখন Cursor একটি কার্যকরী পদ্ধতি হতে পারে। SET-based operations এবং CTE গুলি Cursor-এর চেয়ে সাধারণত দ্রুত এবং কার্যকরী হয়ে থাকে।

Content added By

CURSOR হলো একটি ডেটাবেস অবজেক্ট যা T-SQL-এ ব্যবহৃত হয় এবং এটি Row-by-Row Processing বা অর্থাৎ রেকর্ড ভিত্তিক প্রক্রিয়া পরিচালনা করতে সাহায্য করে। যখন আপনি কোনো কুয়েরি চালান, তখন SQL Server পুরো টেবিল বা ডেটা সেগমেন্টে একবারে কাজ করে, তবে কিছু ক্ষেত্রে আপনি একেকটি রেকর্ডকে পর্যায়ক্রমে বা একে একে প্রক্রিয়া করতে চান। এই কাজটি CURSOR এর মাধ্যমে করা হয়।

CURSOR একাধিক রেকর্ডের উপর কাজ করার জন্য একটি টুল, তবে এটি SET-BASED পদ্ধতির পরিবর্তে ROW-BASED পদ্ধতি ব্যবহার করে, যা ডেটার প্রতি রেকর্ড আলাদাভাবে কাজ করে।

CURSOR এর ধারণা

CURSOR হল একটি ডেটাবেস অবজেক্ট যা ডেটাবেস টেবিলের রেকর্ডগুলিকে একটি সারির মধ্যে ইটারেট বা পর্যায়ক্রমে প্রসেস করতে ব্যবহৃত হয়। সাধারণত, SET-BASED অপারেশনগুলো দ্রুত হয়, কিন্তু যখন আপনার Row-by-Row অপারেশন প্রয়োজন হয়, তখন CURSOR উপকারী হতে পারে।

CURSOR এর মূল কাজের পদক্ষেপ:

  1. DECLARE: প্রথমে ক্যানভাস তৈরি করতে CURSOR ডিফাইন করতে হয়।
  2. OPEN: CURSOR ওপেন করার মাধ্যমে, টেবিল বা কুয়েরি রেজাল্টের মধ্যে রেকর্ডগুলো একত্রিত করা হয়।
  3. FETCH: একে একে রেকর্ডগুলোকে FETCH কমান্ডের মাধ্যমে প্রক্রিয়া করা হয়।
  4. CLOSE: যখন সব রেকর্ড প্রক্রিয়া করা হয়ে যায়, তখন CURSOR বন্ধ করা হয়।
  5. DEALLOCATE: CURSOR রিসোর্স মুক্ত করতে DEALLOCATE কমান্ড ব্যবহার করা হয়।

CURSOR এর সিনট্যাক্স:

DECLARE cursor_name CURSOR FOR
    SELECT column1, column2
    FROM table_name
    WHERE condition;

OPEN cursor_name;

FETCH NEXT FROM cursor_name INTO @var1, @var2;

WHILE @@FETCH_STATUS = 0
BEGIN
    -- Process each row here

    FETCH NEXT FROM cursor_name INTO @var1, @var2;
END;

CLOSE cursor_name;
DEALLOCATE cursor_name;

CURSOR এর উদাহরণ

ধরা যাক, একটি Employees টেবিল আছে, যেখানে EmployeeID, FirstName, LastName কলাম রয়েছে। আপনি যদি প্রতিটি কর্মচারীর তথ্য নিয়ে কিছু কাজ করতে চান, তাহলে আপনি CURSOR ব্যবহার করতে পারেন।

DECLARE @EmployeeID INT, @FirstName VARCHAR(50), @LastName VARCHAR(50);

DECLARE EmployeeCursor CURSOR FOR
SELECT EmployeeID, FirstName, LastName
FROM Employees;

OPEN EmployeeCursor;

FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @FirstName, @LastName;

WHILE @@FETCH_STATUS = 0
BEGIN
    -- এখানে আপনি রেকর্ডের উপর কাজ করতে পারেন
    PRINT 'Employee ID: ' + CAST(@EmployeeID AS VARCHAR(10)) + ', Name: ' + @FirstName + ' ' + @LastName;

    -- পরবর্তী রেকর্ডে যান
    FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @FirstName, @LastName;
END;

CLOSE EmployeeCursor;
DEALLOCATE EmployeeCursor;

এখানে:

  • DECLARE: EmployeeCursor নামে একটি CURSOR তৈরি করা হয়েছে যা Employees টেবিলের EmployeeID, FirstName, এবং LastName রেকর্ড গুলো ধারণ করবে।
  • FETCH NEXT: একে একে রেকর্ড গুলি পড়া এবং পরবর্তী রেকর্ডে যাওয়া।
  • @@FETCH_STATUS: এটি চেক করে যে, বর্তমানে CURSOR কোনো রেকর্ড নিয়ে কাজ করছে কিনা।

CURSOR এর প্রকার

  1. STATIC CURSOR: এটি ডেটা সংগ্রহ করে এবং যেকোনো পরিবর্তন থেকে আলাদা হয়ে কাজ করে। এটি রেকর্ডগুলির মধ্যে পরিবর্তন মেনে চলে না।
  2. DYNAMIC CURSOR: এটি টেবিলের বা কুয়েরির রেকর্ডে করা সকল পরিবর্তন মেনে চলে। এর মানে, যদি অন্য ব্যবহারকারী কোনো রেকর্ড আপডেট বা ডিলিট করে, তাহলে DYNAMIC CURSOR সেই পরিবর্তন গ্রহণ করবে।
  3. FORWARD_ONLY CURSOR: এটি শুধুমাত্র FETCH NEXT অপারেশন চালায় এবং পূর্ববর্তী রেকর্ডে ফিরে যেতে পারে না। এটি দ্রুততর এবং কম রিসোর্স ব্যবহার করে।
  4. KEYSET CURSOR: এটি একটি স্থির কাস্টম কুয়েরি রেজাল্ট তৈরি করে এবং কুয়েরির সময় পরিবর্তিত রেকর্ডগুলিতে অ্যাক্সেস পায়।

CURSOR ব্যবহারের প্রয়োজনীয়তা

  1. Row-by-Row Processing: যখন আপনি একটি কুয়েরি থেকে রেকর্ডগুলোকে একে একে প্রক্রিয়া করতে চান, তখন CURSOR ব্যবহার করা হয়।
  2. Complex Calculations: যদি আপনাকে একটি কুয়েরির উপর কঠিন বা জটিল গণনা করতে হয় যা SET-BASED পদ্ধতিতে করা সম্ভব না, তাহলে CURSOR সহায়ক হতে পারে।
  3. Dealing with Hierarchical Data: Recursive Data বা Tree Structures এর ক্ষেত্রে CURSOR কার্যকরী হতে পারে।

CURSOR এর সমস্যা এবং এর প্রতিকার

  1. Performance Issues: CURSOR সাধারণত SET-BASED পদ্ধতির তুলনায় কম কার্যকরী, কারণ এটি প্রতিটি রেকর্ডের উপর আলাদা করে কাজ করে, যা কার্যক্ষমতা কমাতে পারে।

    প্রতিকার: যখন সম্ভব, CURSOR এর পরিবর্তে JOINs এবং CTEs ব্যবহার করার চেষ্টা করুন।

  2. Resource Intensive: CURSOR ব্যবহার করার সময় CPU এবং Memory বেশী ব্যবহার হয়, কারণ এটি একে একে প্রতিটি রেকর্ড প্রসেস করে।

    প্রতিকার: শুধুমাত্র খুব প্রয়োজনীয় ক্ষেত্রে CURSOR ব্যবহার করুন এবং OPEN এবং CLOSE করার পরে DEALLOCATE করা নিশ্চিত করুন।


সারাংশ

CURSOR একটি T-SQL অবজেক্ট যা Row-by-Row ডেটা প্রক্রিয়াকরণের জন্য ব্যবহৃত হয়। এটি একে একে রেকর্ড প্রসেস করার জন্য কার্যকরী হতে পারে, তবে এটি SET-BASED পদ্ধতির চেয়ে কম কার্যকরী এবং কম্পিউটার রিসোর্স বেশি ব্যবহার করে। CURSOR সাধারণত জটিল বা রিকর্ষিভ ডেটা প্রক্রিয়াকরণে ব্যবহৃত হয়, তবে পারফরম্যান্সের দিক থেকে যখন সম্ভব, তখন JOIN বা CTE ব্যবহার করা উচিত।

Content added By

CURSOR T-SQL-এ একটি প্রোগ্রামিং কনসেপ্ট যা আপনাকে একাধিক রেকর্ডের উপর কার্যক্রম চালানোর জন্য প্রতিটি রেকর্ড আলাদাভাবে প্রক্রিয়া করার সুযোগ প্রদান করে। সাধারণ SQL কোয়েরি একসাথে একাধিক রেকর্ড পরিচালনা করে, কিন্তু CURSOR প্রতিটি রেকর্ডকে একে একে (Row-By-Row) প্রক্রিয়া করতে ব্যবহৃত হয়। এটি তখন কার্যকরী হয় যখন SQL স্টেটমেন্ট দিয়ে একাধিক রেকর্ড পরিচালনা করা সম্ভব না, এবং আপনাকে প্রতিটি রেকর্ডের জন্য আলাদা কোনো কাজ করতে হয়।

CURSOR এর মৌলিক স্টেপস

  1. DECLARE CURSOR: একটি CURSOR ঘোষণা করা হয়, যা ডেটাবেসের রেকর্ডগুলো লোড করে।
  2. OPEN CURSOR: CURSORটি খুলে সেটি প্রক্রিয়া করার জন্য প্রস্তুত করা হয়।
  3. FETCH: CURSOR থেকে পরবর্তী রেকর্ডটি নেওয়া হয়।
  4. PROCESSING: FETCH করা রেকর্ডটি প্রক্রিয়া করা হয়।
  5. CLOSE CURSOR: CURSOR বন্ধ করা হয়।
  6. DEALLOCATE CURSOR: CURSOR মেমোরি থেকে মুক্ত করা হয়।

CURSOR সিনট্যাক্স

DECLARE cursor_name CURSOR FOR
    SELECT column1, column2, ...
    FROM table_name
    WHERE condition;

OPEN cursor_name;

FETCH NEXT FROM cursor_name INTO @variable1, @variable2, ...;

WHILE @@FETCH_STATUS = 0
BEGIN
    -- Process the data
    -- Example: PRINT the data or perform calculations

    FETCH NEXT FROM cursor_name INTO @variable1, @variable2, ...;
END

CLOSE cursor_name;
DEALLOCATE cursor_name;
  • cursor_name: CURSOR এর নাম।
  • SELECT: যে SELECT কুয়েরি দিয়ে CURSOR এর রেকর্ড তৈরি করা হবে।
  • FETCH NEXT: পরবর্তী রেকর্ডটি নেওয়া হয় এবং সেটি ভ্যারিয়েবলে লোড করা হয়।
  • @@FETCH_STATUS: এই সিস্টেম ফাংশন CURSOR এর বর্তমান অবস্থান চেক করে। যদি FETCH সফল হয়, তবে এটি 0 ফেরত দেয়।

উদাহরণ: CURSOR এর মাধ্যমে Row-By-Row প্রসেসিং

ধরা যাক, আপনার কাছে একটি Employees টেবিল আছে এবং আপনি প্রতিটি কর্মচারীর Salary কে ১০% বৃদ্ধি করতে চান। এটি করার জন্য, CURSOR ব্যবহার করা যেতে পারে:

DECLARE @EmployeeID INT, @Salary DECIMAL(10, 2);

DECLARE employee_cursor CURSOR FOR
    SELECT EmployeeID, Salary
    FROM Employees
    WHERE Department = 'HR';

OPEN employee_cursor;

FETCH NEXT FROM employee_cursor INTO @EmployeeID, @Salary;

WHILE @@FETCH_STATUS = 0
BEGIN
    -- Process each row
    UPDATE Employees
    SET Salary = @Salary * 1.10
    WHERE EmployeeID = @EmployeeID;

    -- Fetch the next row
    FETCH NEXT FROM employee_cursor INTO @EmployeeID, @Salary;
END

CLOSE employee_cursor;
DEALLOCATE employee_cursor;

এখানে:

  • DECLARE CURSOR: employee_cursor নামে একটি CURSOR ঘোষণা করা হয়েছে, যা Employees টেবিলের EmployeeID এবং Salary নিয়ে কাজ করবে।
  • OPEN: CURSOR খুলে দেওয়া হয়েছে এবং রেকর্ড নির্বাচন করা হয়েছে।
  • FETCH NEXT: প্রথম রেকর্ডটি নেওয়া হয়েছে এবং এটি ভ্যারিয়েবলগুলিতে স্টোর করা হয়েছে।
  • UPDATE: প্রতিটি রেকর্ডের জন্য Salary-কে ১০% বৃদ্ধি করা হয়েছে।
  • WHILE: @@FETCH_STATUS = 0 নিশ্চিত করে যে CURSOR আরো রেকর্ড পাবার পর পরবর্তী রেকর্ডটি FETCH NEXT এর মাধ্যমে প্রসেস করা হবে।
  • CLOSE & DEALLOCATE: শেষে CURSOR বন্ধ এবং মেমরি থেকে মুক্ত করা হয়েছে।

CURSOR এর সুবিধা

  1. Row-By-Row প্রক্রিয়াকরণ: যখন আপনাকে একাধিক রেকর্ডের উপর শর্তবিশেষে আলাদাভাবে কাজ করতে হয়, তখন CURSOR খুবই কার্যকর।
  2. কমপ্লেক্স লজিক প্রয়োগ: কিছু নির্দিষ্ট লজিকের জন্য যখন আপনাকে প্রতিটি রেকর্ডে আলাদা কাজ করতে হয়, CURSOR ব্যবহার করা যেতে পারে।
  3. ডেটাবেস আপডেট করা: CURSOR এর মাধ্যমে আপনি প্রতিটি রেকর্ডে প্রক্রিয়া বা গণনা করতে পারেন এবং তারপর ডেটাবেসে সেই পরিবর্তনগুলো আপডেট করতে পারেন।

CURSOR এর অসুবিধা

  1. পারফরম্যান্সের সমস্যা: CURSOR প্রক্রিয়া সাধারণ SQL স্টেটমেন্টের তুলনায় ধীর গতিতে চলে। কারণ এটি একে একে রেকর্ড প্রক্রিয়া করে, তাই বড় ডেটাসেটের জন্য এটি বেশ সময়সাপেক্ষ হতে পারে।
  2. ডেটাবেস লকিং: CURSOR ব্যবহার করলে প্রতিটি রেকর্ডে লকিং হতে পারে, যা অন্যান্য ট্রানজ্যাকশনকে প্রভাবিত করতে পারে।
  3. পরিষ্কারকরণ: CURSOR ব্যবহারের পরে অবশ্যই CLOSE এবং DEALLOCATE করতে হয়, অন্যথায় মেমরি লিক হতে পারে।

CURSOR Alternatives (বিকল্প)

  1. SET Based Operations: যদি সম্ভব হয়, SET-based SQL operations (যেমন UPDATE, SELECT, INSERT) ব্যবহার করা ভালো, কারণ এগুলি অনেক দ্রুত এবং পারফরম্যান্সের জন্য বেশি উপকারী।

    উদাহরণ:

    UPDATE Employees
    SET Salary = Salary * 1.10
    WHERE Department = 'HR';
    
  2. CTE (Common Table Expression): CTE ব্যবহার করে কিছু কার্যক্রম আরও কার্যকরভাবে করা যেতে পারে, বিশেষত যখন ট্রানজ্যাকশনাল ডেটা ম্যানিপুলেশন করতে হয়।

সারাংশ

CURSOR T-SQL-এ একটি অত্যন্ত শক্তিশালী টুল যা Row-By-Row প্রসেসিং করার জন্য ব্যবহৃত হয়। এটি একটি সময়সাপেক্ষ অপারেশন, তবে কখনো কখনো এটি ব্যবহার করা প্রয়োজন হতে পারে যখন আপনাকে প্রতিটি রেকর্ডের উপর আলাদাভাবে কাজ করতে হয়। তবে, সাধারণত SET-based operations ব্যবহার করা উচিত, কারণ তা অনেক দ্রুত এবং বেশি পারফরম্যান্স-ভিত্তিক হয়।

Content added By

Cursors হল SQL Server-এ এমন একটি ডেটা অবজেক্ট যা একাধিক রেকর্ডের উপর ইটারেট (iterate) করার জন্য ব্যবহৃত হয়। সাধারণত, যখন আপনি একাধিক রেকর্ডের উপর অপারেশন করতে চান, যেমন আপডেট বা ডিলিট, তখন Cursor ব্যবহার করা হয়।

SQL Server-এ বিভিন্ন ধরনের cursors রয়েছে, তার মধ্যে Static এবং Dynamic হল দুটি জনপ্রিয় ধরনের cursor। এই দুই ধরনের cursor বিভিন্ন প্রয়োজনে ব্যবহার করা হয়, এবং তাদের নিজস্ব বৈশিষ্ট্য এবং সীমাবদ্ধতা রয়েছে।


১. Static Cursor

Static Cursor হল একটি ধরনের cursor যা ডেটাবেসের একটি নির্দিষ্ট মুহূর্তে টেবিল বা কুয়েরি থেকে ডেটা একটি স্ট্যাটিক (স্থির) কপি তৈরি করে। এটি ডেটার উপর ইটারেট করার সময় টেবিলের সাথে কোনো পরিবর্তন (যেমন INSERT, UPDATE, DELETE) ঘটলে সেই পরিবর্তনগুলি কীভাবে প্রতিফলিত হয় না

Static Cursor এর বৈশিষ্ট্য:

  • এটি একবার ডেটা ক্যাশ (cache) করে, তারপর ডেটার সাথে কোনো পরিবর্তন হলে তা প্রতিফলিত হয় না।
  • READ_ONLY অপারেশনগুলির জন্য উপযুক্ত।
  • ডেটার উপর নির্দিষ্ট অ্যাকশন যেমন এক্সট্রা ডেটা পরিবর্তন করা বা তথ্য থেকে ইনসার্ট করা সম্ভব নয়।
  • সিস্টেম রিসোর্স কম ব্যবহার করে কারণ এটি ডেটার কপি তৈরি করে এবং পরবর্তীতে সেই কপি থেকেই ডেটা নিয়ে কাজ করে।

Static Cursor তৈরি করা:

DECLARE @EmployeeID INT, @EmployeeName NVARCHAR(100);

DECLARE EmployeeCursor STATIC CURSOR FOR
SELECT EmployeeID, Name FROM Employees;

OPEN EmployeeCursor;

FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @EmployeeName;

WHILE @@FETCH_STATUS = 0
BEGIN
    PRINT 'EmployeeID: ' + CAST(@EmployeeID AS NVARCHAR) + ', Name: ' + @EmployeeName;
    FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @EmployeeName;
END

CLOSE EmployeeCursor;
DEALLOCATE EmployeeCursor;

এখানে:

  • STATIC টাইপের cursor ব্যবহার করা হয়েছে।
  • কুয়েরি থেকে সমস্ত কর্মী আইডি এবং নামের কপি তৈরি হয়েছে এবং সেগুলোর উপর ইটারেট করা হচ্ছে।

২. Dynamic Cursor

Dynamic Cursor হল একটি ধরনের cursor যা ডেটাবেসের সাথে ক্রমাগত সিঙ্ক্রোনাইজ থাকে। অর্থাৎ, এটি যখন টেবিল বা কুয়েরির উপর কাজ করে, তখন কোনো পরিবর্তন (যেমন INSERT, UPDATE, DELETE) ঘটলে সেই পরিবর্তনগুলো কনটিনিউয়াসলি প্রতিফলিত হয়।

Dynamic Cursor এর বৈশিষ্ট্য:

  • এটি real-time ডেটার সাথে কাজ করে এবং টেবিলের পরিবর্তনগুলো দেখায়।
  • INSERT, UPDATE, DELETE অপারেশনগুলির মাধ্যমে ডেটা পরিবর্তন করলে, সেই পরিবর্তনগুলি অবিলম্বে cursor-এ প্রতিফলিত হয়।
  • এটি বেশিরভাগ ক্ষেত্রে বেশি রিসোর্স ব্যবহার করে, কারণ এটি সার্ভারের ডেটা পরিবর্তনের সাথে সিঙ্ক্রোনাইজ থাকে।
  • এটি READ_WRITE অপারেশনগুলি (তথ্য আপডেট বা মুছে ফেলা) সমর্থন করে।

Dynamic Cursor তৈরি করা:

DECLARE @EmployeeID INT, @EmployeeName NVARCHAR(100);

DECLARE EmployeeCursor DYNAMIC CURSOR FOR
SELECT EmployeeID, Name FROM Employees;

OPEN EmployeeCursor;

FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @EmployeeName;

WHILE @@FETCH_STATUS = 0
BEGIN
    PRINT 'EmployeeID: ' + CAST(@EmployeeID AS NVARCHAR) + ', Name: ' + @EmployeeName;
    FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @EmployeeName;
END

CLOSE EmployeeCursor;
DEALLOCATE EmployeeCursor;

এখানে:

  • DYNAMIC টাইপের cursor ব্যবহার করা হয়েছে।
  • টেবিলের ডেটার সাথে সিঙ্ক্রোনাইজড থেকে আপডেট, ইনসার্ট এবং ডিলিট পরিবর্তনগুলোকে ট্র্যাক করে ইটারেট করা হচ্ছে।

Static এবং Dynamic Cursors এর মধ্যে পার্থক্য

বৈশিষ্ট্যStatic CursorDynamic Cursor
ডেটার আপডেটএকবার ডেটা ক্যাশ করে, পরবর্তীতে কোনো পরিবর্তন প্রতিফলিত হয় না।ডেটাবেসে হওয়া কোনো পরিবর্তন তাত্ক্ষণিকভাবে প্রতিফলিত হয়।
পারফরম্যান্সসাধারণত দ্রুত, কারণ এটি ডেটার স্থির কপি ব্যবহার করে।সিস্টেম রিসোর্স বেশি ব্যবহার করে কারণ এটি ডেটাবেসের সাথে সিঙ্ক্রোনাইজ থাকে।
ব্যবহারযোগ্যতাসাধারণত READ_ONLY অপারেশনগুলির জন্য ব্যবহার হয়।READ_WRITE অপারেশন (INSERT, UPDATE, DELETE) সমর্থন করে।
ডেটার সিঙ্ক্রোনাইজেশনডেটা পরিবর্তন হলে তা প্রতিফলিত হয় না।ডেটা পরিবর্তন হলে তা সিঙ্ক্রোনাইজ হয়ে যায়।

কেন কোনটি ব্যবহার করবেন?

  • Static Cursor: আপনি যদি ডেটাবেসের উপর শুধু READ_ONLY অপারেশন করতে চান এবং ডেটার স্থির কপি ব্যবহার করে দ্রুত ফলাফল চান, তবে Static Cursor ব্যবহার করা শ্রেয়। উদাহরণস্বরূপ, যদি আপনি একবার ডেটা নিয়ে সেটির উপর কাজ করতে চান এবং পরবর্তীতে কোনো পরিবর্তন না চান।
  • Dynamic Cursor: আপনি যদি READ_WRITE অপারেশন করতে চান এবং ডেটার উপর পরিবর্তন বা আপডেট করতে চান, এবং আপনি চান যে ডেটাবেসের পরিবর্তন গুলি অবিলম্বে cursor-এ প্রতিফলিত হোক, তবে Dynamic Cursor ব্যবহার করুন। এটি সাধারণত বেশি রিসোর্স ব্যবহার করে, কিন্তু এটি ডেটাবেসের পরিবর্তনগুলির সাথে সিঙ্ক্রোনাইজ থাকে।

সারাংশ:

  • Static Cursors একটি স্থির কপি তৈরি করে এবং ডেটার মধ্যে কোনো পরিবর্তন প্রতিফলিত হয় না।
  • Dynamic Cursors ডেটাবেসের সাথে ক্রমাগত সিঙ্ক্রোনাইজ থাকে এবং কোনো পরিবর্তন হলে তা অবিলম্বে প্রতিফলিত হয়।
  • Static Cursor বেশি পারফরম্যান্স এবং কম রিসোর্স ব্যবহার করে, তবে Dynamic Cursor অধিক রিসোর্স ব্যবহার করে এবং ডেটার সঠিক অবস্থায় কাজ করতে সহায়তা করে।
Content added By

Cursor SQL Server-এ এমন একটি ডেটাবেস অবজেক্ট যা একাধিক রেকর্ডের উপর ইটারেট (iterate) করার জন্য ব্যবহৃত হয়। এটি ডেটার উপর একে একে অপারেশন (যেমন: UPDATE, DELETE, SELECT) করার সুযোগ প্রদান করে। যখন আপনি একটি কুয়েরি থেকে একাধিক রেকর্ড নিয়ে কাজ করতে চান, তখন cursor ব্যবহার করা হয়।

এখানে Cursor এর সাধারণ ব্যবহার এবং উদাহরণ দেওয়া হলো:


Cursor তৈরি, ব্যবহার এবং শেষ করা

  1. Cursor তৈরি করা:
    • প্রথমে DECLARE কমান্ড দিয়ে cursor ঘোষণা করতে হবে।
    • তারপর, OPEN কমান্ড দিয়ে cursor খুলতে হবে।
    • পরবর্তীতে FETCH NEXT কমান্ড দিয়ে cursor এর মধ্যে ইটারেট করতে হবে।
    • শেষে, CLOSE এবং DEALLOCATE কমান্ড দিয়ে cursor বন্ধ এবং মুক্ত করতে হবে।

উদাহরণ ১: Cursor ব্যবহার করে সকল কর্মী প্রদর্শন

ধরা যাক, আমাদের একটি Employees টেবিল আছে, যেখানে কর্মীদের তথ্য রয়েছে, এবং আমরা cursor ব্যবহার করে তাদের নাম এবং পদের তালিকা দেখাতে চাই।

Step 1: Cursor ঘোষণা এবং ব্যবহার

DECLARE @EmployeeID INT, @EmployeeName NVARCHAR(100), @EmployeePosition NVARCHAR(100);

-- Cursor তৈরি করা
DECLARE EmployeeCursor CURSOR FOR
SELECT EmployeeID, Name, Position FROM Employees;

-- Cursor খোলা
OPEN EmployeeCursor;

-- প্রথম রেকর্ড আনতে FETCH NEXT ব্যবহার করা
FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @EmployeeName, @EmployeePosition;

-- Loop এর মাধ্যমে সমস্ত রেকর্ড ইটারেট করা
WHILE @@FETCH_STATUS = 0
BEGIN
    PRINT 'EmployeeID: ' + CAST(@EmployeeID AS NVARCHAR) + ', Name: ' + @EmployeeName + ', Position: ' + @EmployeePosition;
    
    -- পরবর্তী রেকর্ডের জন্য FETCH NEXT
    FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @EmployeeName, @EmployeePosition;
END;

-- Cursor বন্ধ করা
CLOSE EmployeeCursor;

-- Cursor মুক্ত করা
DEALLOCATE EmployeeCursor;

এখানে:

  • EmployeeCursor নামে একটি cursor তৈরি করা হয়েছে যা EmployeeID, Name, এবং Position কলামগুলোর উপর ইটারেট করবে।
  • FETCH NEXT কমান্ডের মাধ্যমে প্রতিটি রেকর্ডে গিয়ে EmployeeID, Name, এবং Position প্রিন্ট করা হয়েছে।

উদাহরণ ২: Cursor ব্যবহার করে বেতন আপডেট করা

ধরা যাক, আপনি কর্মীদের বেতন আপডেট করতে চান। যদি তাদের Position 'Manager' হয়, তাহলে তাদের বেতন ১০% বাড়াতে হবে। এখানে cursor ব্যবহার করে আমরা এই কাজটি করতে পারি।

DECLARE @EmployeeID INT, @CurrentSalary DECIMAL(10, 2), @NewSalary DECIMAL(10, 2), @Position NVARCHAR(100);

-- Cursor তৈরি করা
DECLARE EmployeeCursor CURSOR FOR
SELECT EmployeeID, Salary, Position FROM Employees;

-- Cursor খোলা
OPEN EmployeeCursor;

-- প্রথম রেকর্ড আনতে FETCH NEXT ব্যবহার করা
FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @CurrentSalary, @Position;

-- Loop এর মাধ্যমে সমস্ত রেকর্ড ইটারেট করা
WHILE @@FETCH_STATUS = 0
BEGIN
    -- যদি কর্মীর পদের নাম 'Manager' হয়, তার বেতন ১০% বাড়ানো
    IF @Position = 'Manager'
    BEGIN
        SET @NewSalary = @CurrentSalary * 1.10; -- ১০% বাড়ানো
        UPDATE Employees
        SET Salary = @NewSalary
        WHERE EmployeeID = @EmployeeID;
    END;

    -- পরবর্তী রেকর্ডের জন্য FETCH NEXT
    FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @CurrentSalary, @Position;
END;

-- Cursor বন্ধ করা
CLOSE EmployeeCursor;

-- Cursor মুক্ত করা
DEALLOCATE EmployeeCursor;

এখানে:

  • EmployeeCursor তৈরি করা হয়েছে যা EmployeeID, Salary, এবং Position কলামের উপর ইটারেট করবে।
  • প্রতিটি কর্মীর Position চেক করা হচ্ছে এবং যদি Manager হয়, তাহলে তার বেতন ১০% বৃদ্ধি করা হচ্ছে।

উদাহরণ ৩: Cursor ব্যবহার করে রেকর্ড ডিলিট করা

ধরা যাক, আপনার Employees টেবিল থেকে সকল কর্মীকে 'Inactive' স্ট্যাটাস দেওয়া হয়েছে এবং আপনি Inactive স্ট্যাটাসের সকল কর্মীকে ডিলিট করতে চান। এখানে cursor ব্যবহার করে এটি করা যাবে।

DECLARE @EmployeeID INT, @Status NVARCHAR(20);

-- Cursor তৈরি করা
DECLARE EmployeeCursor CURSOR FOR
SELECT EmployeeID, Status FROM Employees WHERE Status = 'Inactive';

-- Cursor খোলা
OPEN EmployeeCursor;

-- প্রথম রেকর্ড আনতে FETCH NEXT ব্যবহার করা
FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @Status;

-- Loop এর মাধ্যমে সমস্ত রেকর্ড ইটারেট করা
WHILE @@FETCH_STATUS = 0
BEGIN
    -- Inactive স্ট্যাটাসের কর্মী ডিলিট করা
    DELETE FROM Employees WHERE EmployeeID = @EmployeeID;

    -- পরবর্তী রেকর্ডের জন্য FETCH NEXT
    FETCH NEXT FROM EmployeeCursor INTO @EmployeeID, @Status;
END;

-- Cursor বন্ধ করা
CLOSE EmployeeCursor;

-- Cursor মুক্ত করা
DEALLOCATE EmployeeCursor;

এখানে:

  • EmployeeCursor তৈরি করা হয়েছে যেটি শুধুমাত্র Inactive স্ট্যাটাসের কর্মীদের নির্বাচন করবে।
  • পরে, সেই কর্মীদের DELETE করে ডিলিট করা হয়েছে।

Cursor এর ব্যবহার কবে উপযুক্ত?

  • Cursor সাধারণত তখন ব্যবহার করা হয় যখন আপনাকে একাধিক রেকর্ডের উপর একের পর এক অপারেশন করতে হয়, যা set-based অপারেশন দ্বারা সহজে করা সম্ভব নয়।
  • তবে, Cursor ব্যবহারের সময় মনে রাখতে হবে যে এটি ডেটাবেসের পারফরম্যান্সে প্রভাব ফেলতে পারে, বিশেষ করে যখন রেকর্ডের সংখ্যা বড় হয়।
  • সাধারনত, যখন set-based অপারেশন ব্যবহার করা সম্ভব, তখন তা Cursor ব্যবহার করার চেয়ে অনেক দ্রুত এবং দক্ষ হয়।

সারাংশ

  • Cursor হল SQL-এ ডেটার উপর একে একে কাজ করার একটি উপায়, যা একাধিক রেকর্ডের উপর ক্রমাগত অপারেশন করতে ব্যবহৃত হয়।
  • এটি তৈরি, খুলতে, চলমান রাখতে এবং শেষ করতে DECLARE, OPEN, FETCH NEXT, CLOSE, এবং DEALLOCATE কমান্ড ব্যবহার করা হয়।
  • Cursor ব্যবহারের প্রধান সুবিধা হলো আপনি ডেটার উপর নিয়ন্ত্রণ রেখে একে একে অপারেশন করতে পারেন, তবে এটি পারফরম্যান্সের উপর কিছুটা প্রভাব ফেলতে পারে এবং set-based অপারেশনগুলির চেয়ে কম কার্যকরী হতে পারে।
Content added By
Promotion

Are you sure to start over?

Loading...