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

MySQL SUM json मानों को json कुंजियों द्वारा समूहीकृत किया जाता है

टीएल; डॉ: हां, यह मुख्य नामों को पहले से जाने बिना किया जा सकता है, और किसी भी वैकल्पिक डेटा प्रारूप का मूल पर कोई लाभ नहीं है।

यह मुख्य नामों को पहले से जाने बिना किया जा सकता है लेकिन यह दर्दनाक है ... मूल रूप से आपको तालिका में प्रत्येक मान को तालिका में अलग-अलग कुंजियों के सेट को निर्धारित करने से पहले देखना होगा। इस आवश्यकता के कारण, और तथ्य यह है कि वैकल्पिक डेटा प्रारूपों में प्रति प्रविष्टि एकाधिक कुंजियां हो सकती हैं, उनमें से किसी का उपयोग करने का कोई फायदा नहीं है।

चूंकि आपको सभी अलग-अलग कुंजियों की तलाश करनी होती है, इसलिए जब आप उन्हें ढूंढ रहे होते हैं तो योग करना उतना ही आसान होता है। यह कार्य और प्रक्रिया एक साथ ऐसा करेगी। फ़ंक्शन, json_merge_sum , दो JSON मान लेता है और उन्हें मर्ज करता है, उन मानों का योग करता है जहां एक कुंजी दोनों मानों में दिखाई देती है उदा।

SELECT json_sum_merge('{"key1": 1, "key2": 3}', '{"key3": 1, "key2": 2}')

आउटपुट:

{"key1": 1, "key2": 5, "key3": 1}

फ़ंक्शन कोड:

DELIMITER //
DROP FUNCTION IF EXISTS json_merge_sum //
CREATE FUNCTION json_sum_merge(IN j1 JSON, IN total JSON) RETURNS JSON
BEGIN
  DECLARE knum INT DEFAULT 0;
  DECLARE jkeys JSON DEFAULT JSON_KEYS(j1);
  DECLARE kpath VARCHAR(20);
  DECLARE v INT;
  DECLARE l INT DEFAULT JSON_LENGTH(jkeys);
  kloop: LOOP
    IF knum >= l THEN
      LEAVE kloop;
    END IF;
    SET kpath = CONCAT('$.', JSON_EXTRACT(jkeys, CONCAT('$[', knum, ']')));
    SET v = JSON_EXTRACT(j1, kpath);
    IF JSON_CONTAINS_PATH(total, 'one', kpath) THEN
      SET total = JSON_REPLACE(total, kpath, JSON_EXTRACT(total, kpath) + v);
    ELSE
      SET total = JSON_SET(total, kpath, v);
    END IF;
    SET knum = knum + 1;
  END LOOP kloop;
  RETURN total;
END

प्रक्रिया, count_keys , GROUP BY . के समकक्ष कार्य करता है खंड। यह col1 . के सभी विशिष्ट मान ढूंढता है तालिका में और फिर json_sum_merge पर कॉल करें प्रत्येक पंक्ति के लिए जिसका वह मान col1 . है . ध्यान दें कि पंक्ति चयन क्वेरी SELECT ... INTO . निष्पादित करती है एक डमी चर ताकि कोई आउटपुट उत्पन्न न हो, और एक MIN() . का उपयोग करता है यह सुनिश्चित करने के लिए कि केवल एक ही परिणाम है (ताकि इसे एक चर को सौंपा जा सके)।

प्रक्रिया:

DELIMITER //
DROP PROCEDURE IF EXISTS count_keys //
CREATE PROCEDURE count_keys()
BEGIN
  DECLARE finished INT DEFAULT 0;
  DECLARE col1val VARCHAR(20);
  DECLARE col1_cursor CURSOR FOR SELECT DISTINCT col1 FROM table2;
  DECLARE CONTINUE HANDLER FOR NOT FOUND SET finished=1;
  OPEN col1_cursor;
  col1_loop: LOOP
    FETCH col1_cursor INTO col1val;
    IF finished=1 THEN
      LEAVE col1_loop;
    END IF;
    SET @total = '{}';
    SET @query = CONCAT("SELECT MIN(@total:=json_sum_merge(col2, @total)) INTO @json FROM table2 WHERE col1='", col1val, "'");
    PREPARE stmt FROM @query;
    EXECUTE stmt;
    DEALLOCATE PREPARE stmt;
    SELECT col1val AS col1, @total AS col2;
  END LOOP col1_loop;
END

थोड़े बड़े उदाहरण के लिए:

col1    col2    
aaa     {"key1": 1, "key2": 3}
bbb     {"key1": 4, "key2": 2}
aaa     {"key1": 50, "key3": 0}
ccc     {"key2": 5, "key3": 1, "key4": 3}
bbb     {"key1": 5, "key2": 1, "key5": 3}

CALL count_keys() उत्पादन करता है:

col1    col2    
aaa     {"key1": 51, "key2": 3, "key3": 0}
bbb     {"key1": 9, "key2": 3, "key5": 3}
ccc     {"key2": 5, "key3": 1, "key4": 3}

नोट मैंने टेबल को table2 कहा है इस प्रक्रिया में, आपको उसे (दोनों प्रश्नों में) सूट करने के लिए संपादित करना होगा।



  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. क्या यह अजीब है कि मेरा SQLAlchemy MySQL कनेक्शन हमेशा सो रहा है?

  3. MySQL JDBC ड्राइवर कनेक्शन स्ट्रिंग क्या है?

  4. MySQL समूह लगातार पंक्तियों द्वारा

  5. निष्पादन विवरण के दौरान पीडीओ प्रभावित पंक्तियाँ थीं