Mysql
 sql >> डेटाबेस >  >> RDS >> Mysql

हम किसी तालिका में किसी फ़ील्ड द्वारा गतिशील क्रम को कैसे नियंत्रित करते हैं?

अगर मैं आपको सही समझता हूं तो आपको position . में मानों के अनुक्रम को ठीक से प्रबंधित करने के लिए एक तरीके की आवश्यकता है कॉलम जब आप नए प्रश्न सम्मिलित करते हैं, किसी मौजूदा की स्थिति बदलते हैं या प्रश्न हटाते हैं।

मान लें कि आपकी प्रश्न तालिका का निम्नलिखित डीडीएल है:

CREATE TABLE `questions` (
    `id` int(11) UNSIGNED NOT NULL AUTO_INCREMENT,
    `question` VARCHAR(256) DEFAULT NULL,
    `position` INT(11) DEFAULT NULL,
    PRIMARY KEY (`id`)
);

और प्रारंभिक डेटा इस तरह सेट करें

+----+------------+----------+
| id | question   | position |
+----+------------+----------+
|  1 | Question 1 |        1 |
|  2 | Question 2 |        2 |
|  3 | Question 3 |        3 |
+----+------------+----------+

प्रश्नों की क्रमित सूची प्राप्त करने के लिए आप स्पष्ट करते हैं

SELECT * 
  FROM questions 
 ORDER BY position;

प्रश्न सूची के अंत में एक नया प्रश्न सम्मिलित करने के लिए आप करते हैं

INSERT INTO questions (question, position) 
SELECT 'New Question', COALESCE(MAX(position), 0) + 1
  FROM questions;

परिणाम होगा:

+----+--------------+----------+
| id | question     | position |
+----+--------------+----------+
|  1 | Question 1   |        1 |
|  2 | Question 2   |        2 |
|  3 | Question 3   |        3 |
|  4 | New Question |        4 |
+----+--------------+----------+

किसी विशिष्ट स्थिति में एक नया प्रश्न सम्मिलित करने के लिए (मान लें कि स्थिति 3) सूची में आप इसे दो प्रश्नों के साथ करते हैं:

UPDATE questions
   SET position = position + 1
 WHERE position >= 3;

INSERT INTO questions (question, position) 
VALUES ('Another Question', 3);

अब आपके पास है

+----+------------------+----------+
| id | question         | position |
+----+------------------+----------+
|  1 | Question 1       |        1 |
|  2 | Question 2       |        2 |
|  5 | Another Question |        3 |
|  3 | Question 3       |        4 |
|  4 | New Question     |        5 |
+----+------------------+----------+

दो प्रश्नों की स्थिति बदलने के लिए (उदा. आईडी 2 और 5 वाले प्रश्न) आप करते हैं

UPDATE questions AS q1 INNER JOIN 
       questions AS q2 ON q1.id = 2 AND q2.id = 5
   SET q1.position = q2.position,
       q2.position = q1.position

आइए देखें कि हमें क्या मिला है

+----+------------------+----------+
| id | question         | position |
+----+------------------+----------+
|  1 | Question 1       |        1 |
|  5 | Another Question |        2 |
|  2 | Question 2       |        3 |
|  3 | Question 3       |        4 |
|  4 | New Question     |        5 |
+----+------------------+----------+

ठीक यही आप तब करते हैं जब उपयोगकर्ता आपके ऊपर और नीचे बटन पर क्लिक करता है, सही प्रश्न आईडी प्रदान करता है।

अब यदि आप प्रश्न को हटाते समय अपनी स्थिति को बिना अंतराल के क्रम में रखना चाहते हैं तो आप ऐसा कर सकते हैं।

सूची के अंत से हटाने के लिए आप साधारण डिलीट का उपयोग करते हैं

DELETE FROM questions WHERE id=4;

परिणाम

+----+------------------+----------+
| id | question         | position |
+----+------------------+----------+
|  1 | Question 1       |        1 |
|  5 | Another Question |        2 |
|  2 | Question 2       |        3 |
|  3 | Question 3       |        4 |
+----+------------------+----------+

सूची के बीच में (या शुरुआत में) किसी प्रश्न को हटाना अधिक काम की आवश्यकता है। मान लें कि हम id=5 के साथ प्रश्न को हटाना चाहते हैं

-- Get the current position of question with id=5
SELECT position FROM questions WHERE id=5;
-- Position is 2
-- Now delete the question
DELETE FROM questions WHERE id=5;
-- And update position values
UPDATE questions
   SET position = position - 1
 WHERE position > 2;

और अंत में हमारे पास है

+----+--------------+----------+
| id | question     | position |
+----+--------------+----------+
|  1 | Question 1   |        1 |
|  2 | Question 2   |        2 |
|  3 | Question 3   |        3 |
+----+--------------+----------+

अपडेट करें :हमारे जीवन को आसान बनाने के लिए हम इसे संग्रहीत प्रक्रियाओं में लपेट सकते हैं

DELIMITER $$
CREATE PROCEDURE add_question (q VARCHAR(256), p INT)
BEGIN

IF p IS NULL OR p = 0 THEN
    INSERT INTO questions (question, position) 
    SELECT q, COALESCE(MAX(position), 0) + 1
      FROM questions;
ELSE
    UPDATE questions
       SET position = position + 1
     WHERE position >= p;

    INSERT INTO questions (question, position) 
    VALUES (q, p);
END IF;
END$$
DELIMITER ;

DELIMITER $$
CREATE PROCEDURE swap_questions (q1 INT, q2 INT)
BEGIN
    UPDATE questions AS qs1 INNER JOIN 
           questions AS qs2 ON qs1.id = q1 AND qs2.id = q2
       SET qs1.position = qs2.position,
           qs2.position = qs1.position;
END$$
DELIMITER ;

DELIMITER $$
CREATE PROCEDURE delete_question (q INT)
BEGIN
    SELECT position INTO @cur_pos FROM questions WHERE id=q;
    SELECT MAX(position) INTO @max FROM questions;

    DELETE FROM questions WHERE id=q;

IF @cur_pos <> @max THEN 
    UPDATE questions
       SET position = position - 1
     WHERE position > @cur_pos;
END IF;
END$$
DELIMITER ;

और उनका इस तरह उपयोग करें:

-- Add a question to the end of the list
CALL add_question('How are you today?', 0);
CALL add_question('How are you today?', NULL);

-- Add a question at a specific position
CALL add_question('How do you do today?', 3);

-- Swap questions' positions
CALL swap_questions(1, 7);

-- Delete a question
CALL delete_question(2);



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. परिणाम में जोड़े गए एक नए कॉलम के रूप में ऑटो वृद्धि के साथ परिणामों का चयन करने के लिए MySQL क्वेरी

  2. पीडीओ पीडीओ के साथ चयन करें एक गैर-ऑब्जेक्ट त्रुटि पर सदस्य फ़ंक्शन को कॉल करें ()

  3. फॉर्म विकल्पों के साथ MYSQL क्वेरी को फ़िल्टर करें

  4. .NET EF4.1 + MySQL के साथ क्लास इनहेरिटेंस

  5. मैं mysqldump से डंप फ़ाइल को कैसे पुनर्स्थापित करूं?