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

MYSQL क्वेरी - पोस्ट से संबंधित नवीनतम टिप्पणी प्राप्त करें

यह त्रुटि संदेश

आमतौर पर आपके कॉलम और टेबल की परिभाषा के कारण होता है। इसका आमतौर पर मतलब है कि एक समान चिह्न के दोनों ओर अलग-अलग संयोजन होते हैं। आपको बस एक को चुनना है और उस निर्णय को अपनी क्वेरी में शामिल करना है।

यहां संयोजन समस्या @prev_value के क्रॉस जॉइन में थी जिसका उपयोग करने के लिए एक स्पष्ट संयोजन की आवश्यकता थी।

मैंने "row_number" लॉजिक को सिंगल क्रॉस जॉइन में थोड़ा बदल दिया है और if लॉजिक को सिलेक्ट लिस्ट के चरम पर ले जाया गया है।

कुछ नमूना डेटा नीचे प्रदर्शित किया गया है। प्रश्नों का परीक्षण करने के लिए नमूना डेटा की आवश्यकता है। काम करने वाले उदाहरणों के साथ आपके प्रश्न का उत्तर देने का प्रयास करने वाले किसी भी व्यक्ति को डेटा की आवश्यकता होगी। मैं इसे यहाँ शामिल करने का कारण दुगना है।

  1. ताकि आप मेरे द्वारा प्रस्तुत किसी भी परिणाम को समझ सकें
  2. ताकि भविष्य में जब आप कोई अन्य SQL संबंधित प्रश्न पूछें तो आप डेटा की आपूर्ति के महत्व को समझ सकें। यह न केवल हमारे लिए अधिक सुविधाजनक है कि आप ऐसा करें। यदि पूछने वाला नमूना डेटा प्रदान करता है तो पूछने वाला इसे पहले ही समझ जाएगा - यह किसी अजनबी का आविष्कार नहीं होगा जिसने अपना कुछ समय मदद करने के लिए समर्पित किया है।

नमूना डेटा

कृपया ध्यान दें कि कुछ कॉलम टेबल से गायब हैं, केवल टेबल विवरण में निर्दिष्ट कॉलम शामिल किए गए हैं।

इस नमूना डेटा में एक पोस्ट के खिलाफ 5 टिप्पणियां हैं (कोई पसंद दर्ज नहीं की गई है)

CREATE TABLE Posts 
(
`id` int, 
`uuid` varchar(7) collate utf8_unicode_ci,
`imageLink` varchar(9) collate utf8_unicode_ci, 
`date` datetime
 );
    
INSERT INTO Posts(`id`, `uuid`, `imageLink`, `date`)
VALUES
(145, 'abcdefg', 'blah blah', '2016-10-10 00:00:00') ;

CREATE TABLE   USERS
(
`id` int, 
`username` varchar(15) collate utf8_unicode_ci,
 `profileImage` varchar(12) collate utf8_unicode_ci,
 `date` datetime
) ;
        
INSERT INTO     USERS(`id`, `username`, `profileImage`, `date`)
VALUES
(145, 'used_by_already', 'blah de blah', '2014-01-03 00:00:00') ;
    
    
CREATE TABLE Activity
(
`id` int, 
`uuid` varchar(4) collate utf8_unicode_ci, 
`uuidPost` varchar(7) collate utf8_unicode_ci,
 `type` varchar(40) collate utf8_unicode_ci, 
`commentText` varchar(11) collate utf8_unicode_ci, `date` datetime
) ;
        
INSERT INTO Activity (`id`, `uuid`, `uuidPost`, `type`, `commentText`, `date`)
 VALUES
(345, 'a100', 'abcdefg', 'comment', 'lah lha ha', '2016-07-05 00:00:00'),
(456, 'a101', 'abcdefg', 'comment', 'lah lah lah', '2016-07-06 00:00:00'),
(567, 'a102', 'abcdefg', 'comment', 'lha lha ha', '2016-07-07 00:00:00'),
(678, 'a103', 'abcdefg', 'comment', 'ha lah lah', '2016-07-08 00:00:00'),
(789, 'a104', 'abcdefg', 'comment', 'hla lah lah', '2016-07-09 00:00:00') ;

[एसक्यूएल मानक व्यवहार:प्रति पोस्ट क्वेरी 2 पंक्तियां]

कुछ सुधारों के साथ यह मेरी प्रारंभिक क्वेरी थी। मैंने चयन सूची के कॉलम क्रम को बदल दिया ताकि जब मैं परिणाम प्रस्तुत करूं तो आपको कुछ टिप्पणी संबंधी डेटा आसानी से दिखाई दे। कृपया उन परिणामों का अध्ययन करें जो उन्हें प्रदान किए गए हैं ताकि आप समझ सकें कि क्वेरी क्या करेगी। जिन कारणों से मैंने पहले ही नोट कर लिया है, उनके साथ काम कर रहे नमूना डेटा में # से पहले के कॉलम मौजूद नहीं हैं।

SELECT
      Posts.id
    , Posts.uuid
    , rcom.uuidPost
    , rcom.commentText
    , rcom.`date` commentDate 
    #, Posts.caption
    #, Posts.path
    , Posts.`date`
    , USERS.id
    , USERS.username
    #, USERS.fullname
    , USERS.profileImage
    , COALESCE(A.LikeCNT, 0) num_likes
FROM Posts
INNER JOIN USERS ON Posts.id = 145
            AND USERS.id = 145
LEFT JOIN (
          SELECT
                COUNT(A.uuidPost) LikeCNT
              , A.UUIDPost
          FROM Activity A
          WHERE type = 'like'
          GROUP BY
                A.UUIDPOST
          ) A ON A.UUIDPost = Posts.uuid 
LEFT JOIN (
      SELECT
            @row_num := IF(@prev_value=UUIDPOST,@row_num+1,1) as row_number
          , commentText
          , uuidPost
          , `date`
          , @prev_value := UUIDPOST
      FROM Activity
      CROSS JOIN ( SELECT @row_num := 1, @prev_value := '' collate utf8_unicode_ci  ) xy
      WHERE type = 'comment'
      ORDER BY
            uuidPost
          , `date` DESC
      ) rcom ON rcom.uuidPost  = Posts.UUID
            AND rcom.row_number <= 2
ORDER BY
      posts.`date` DESC
      ;
      
      

SQLFiddle पर इस क्वेरी का कामकाजी प्रदर्शन देखें

परिणाम :

|  id |    uuid | uuidPost | commentText |                   date |                      date |  id |        username | profileImage | num_likes |
|-----|---------|----------|-------------|------------------------|---------------------------|-----|-----------------|--------------|-----------|
| 145 | abcdefg |  abcdefg | hla lah lah | July, 09 2016 00:00:00 | October, 10 2016 00:00:00 | 145 | used_by_already | blah de blah |         0 |
| 145 | abcdefg |  abcdefg |  ha lah lah | July, 08 2016 00:00:00 | October, 10 2016 00:00:00 | 145 | used_by_already | blah de blah |         0 |

2 पंक्तियाँ हैं - जैसा कि अपेक्षित था। सबसे हाल की टिप्पणी के लिए एक पंक्ति, और अगली सबसे हाल की टिप्पणी के लिए दूसरी पंक्तियाँ। यह SQL के लिए सामान्य व्यवहार है और जब तक इस उत्तर के तहत कोई टिप्पणी नहीं जोड़ी जाती, तब तक प्रश्न के पाठक मान लेंगे कि यह सामान्य व्यवहार स्वीकार्य होगा।

प्रश्न में स्पष्ट रूप से स्पष्ट "अपेक्षित परिणाम" का अभाव है।

[विकल्प 1:एक पंक्ति प्रति पोस्ट क्वेरी, UP TO 2 टिप्पणियों के साथ, जोड़े गए कॉलम]

नीचे एक टिप्पणी में यह पता चला था कि आप प्रति पोस्ट 2 पंक्तियाँ नहीं चाहते थे और यह एक आसान समाधान होगा। वैसे यह आसान है लेकिन विकल्प हैं और विकल्प उपयोगकर्ता द्वारा आवश्यकताओं के रूप में निर्धारित किए जाते हैं। यदि प्रश्न का "अपेक्षित परिणाम" था तो हमें पता होगा कि कौन सा विकल्प चुनना है। फिर भी यहाँ एक विकल्प है

SELECT
      Posts.id
    , Posts.uuid
    , max(case when rcom.row_number = 1 then rcom.commentText end) Comment_one
    , max(case when rcom.row_number = 2 then rcom.commentText end) Comment_two
    #, Posts.caption
    #, Posts.path
    , Posts.`date`
    , USERS.id
    , USERS.username
    #, USERS.fullname
    , USERS.profileImage
    , COALESCE(A.LikeCNT, 0) num_likes
FROM Posts
INNER JOIN USERS ON Posts.id = 145
            AND USERS.id = 145
LEFT JOIN (
          SELECT
                COUNT(A.uuidPost) LikeCNT
              , A.UUIDPost
          FROM Activity A
          WHERE type = 'like'
          GROUP BY
                A.UUIDPOST
          ) A ON A.UUIDPost = Posts.uuid 
LEFT JOIN (
      SELECT
            @row_num := IF(@prev_value=UUIDPOST,@row_num+1,1) as row_number
          , commentText
          , uuidPost
          , `date`
          , @prev_value := UUIDPOST
      FROM Activity
      CROSS JOIN ( SELECT @row_num := 1, @prev_value := '' collate utf8_unicode_ci  ) xy
      WHERE type = 'comment'
      ORDER BY
            uuidPost
          , `date` DESC
      ) rcom ON rcom.uuidPost  = Posts.UUID
            AND rcom.row_number <= 2
GROUP BY
      Posts.id
    , Posts.uuid
    #, Posts.caption
    #, Posts.path
    , Posts.`date`
    , USERS.id
    , USERS.username
    #, USERS.fullname
    , USERS.profileImage
    , COALESCE(A.LikeCNT, 0)
ORDER BY
      posts.`date` DESC
      ;

SQLFiddle पर काम करने वाली दूसरी क्वेरी देखें

क्वेरी 2 के परिणाम :

|  id |    uuid | Comment_one | Comment_two |                      date |  id |        username | profileImage | num_likes |
|-----|---------|-------------|-------------|---------------------------|-----|-----------------|--------------|-----------|
| 145 | abcdefg | hla lah lah |  ha lah lah | October, 10 2016 00:00:00 | 145 | used_by_already | blah de blah |         0 |

** विकल्प 2, सबसे हाल की टिप्पणियों को एक अल्पविराम से अलग की गई सूची में संयोजित करें **

SELECT
      Posts.id
    , Posts.uuid
    , group_concat(rcom.commentText) Comments_two_concatenated
    #, Posts.caption
    #, Posts.path
    , Posts.`date`
    , USERS.id
    , USERS.username
    #, USERS.fullname
    , USERS.profileImage
    , COALESCE(A.LikeCNT, 0) num_likes
FROM Posts
INNER JOIN USERS ON Posts.id = 145
            AND USERS.id = 145
LEFT JOIN (
          SELECT
                COUNT(A.uuidPost) LikeCNT
              , A.UUIDPost
          FROM Activity A
          WHERE type = 'like'
          GROUP BY
                A.UUIDPOST
          ) A ON A.UUIDPost = Posts.uuid 
LEFT JOIN (
      SELECT
            @row_num := IF(@prev_value=UUIDPOST,@row_num+1,1) as row_number
          , commentText
          , uuidPost
          , `date`
          , @prev_value := UUIDPOST
      FROM Activity
      CROSS JOIN ( SELECT @row_num := 1, @prev_value := '' collate utf8_unicode_ci  ) xy
      WHERE type = 'comment'
      ORDER BY
            uuidPost
          , `date` DESC
      ) rcom ON rcom.uuidPost  = Posts.UUID
            AND rcom.row_number <= 2
GROUP BY
      Posts.id
    , Posts.uuid
    #, Posts.caption
    #, Posts.path
    , Posts.`date`
    , USERS.id
    , USERS.username
    #, USERS.fullname
    , USERS.profileImage
    , COALESCE(A.LikeCNT, 0)
ORDER BY
      posts.`date` DESC
      

इस तीसरी क्वेरी को SQLFiddle पर काम करते हुए देखें

क्वेरी 3 के परिणाम :

|  id |    uuid | Comments_two_concatenated |                      date |  id |        username | profileImage | num_likes |
|-----|---------|---------------------------|---------------------------|-----|-----------------|--------------|-----------|
| 145 | abcdefg |    hla lah lah,ha lah lah | October, 10 2016 00:00:00 | 145 | used_by_already | blah de blah |         0 |

**सारांश**

मैंने 3 प्रश्न प्रस्तुत किए हैं, प्रत्येक केवल 2 सबसे हाल की टिप्पणियों को दिखाता है, लेकिन प्रत्येक क्वेरी एक अलग तरीके से करती है। पहली क्वेरी (डिफ़ॉल्ट व्यवहार) प्रत्येक पोस्ट के लिए 2 पंक्तियों को प्रदर्शित करेगी। विकल्प 2 एक कॉलम जोड़ता है लेकिन दूसरी पंक्ति को हटा देता है। विकल्प 3 सबसे हाल की 2 टिप्पणियों को जोड़ता है।

कृपया ध्यान दें कि:

  • प्रश्न में सभी स्तंभों को शामिल करने वाली तालिका परिभाषाओं का अभाव है
  • प्रश्न में कोई नमूना डेटा नहीं है, जिससे आपके लिए यहां प्रस्तुत किए गए किसी भी परिणाम को समझना कठिन हो जाता है, लेकिन हमारे लिए समाधान तैयार करना भी कठिन हो जाता है
  • प्रश्न में एक निश्चित "अपेक्षित परिणाम" (वांछित आउटपुट) का भी अभाव है और इसने उत्तर देने में और जटिलता पैदा कर दी है

मुझे उम्मीद है कि अतिरिक्त प्रदान की गई जानकारी कुछ काम की होगी, और अब तक आप यह भी जानते हैं कि SQL के लिए डेटा को कई पंक्तियों के रूप में प्रस्तुत करना सामान्य है। यदि आप उस सामान्य व्यवहार को नहीं चाहते हैं तो कृपया इस बारे में विशिष्ट रहें कि आप अपने प्रश्न में वास्तव में क्या चाहते हैं।

परिशिष्ट भाग। "अनुसरण करता है" के लिए अभी तक एक और सबक्वायरी शामिल करने के लिए आप एक समान सबक्वायरी का उपयोग कर सकते हैं जो आपके पास पहले से है। इसे उस सबक्वेरी से पहले या बाद में जोड़ा जा सकता है। आप इसे sqlfiddle यहां पर उपयोग में भी देख सकते हैं।

LEFT JOIN (
          SELECT
                COUNT(*) FollowCNT
              , IdOtherUser
          FROM Activity
          WHERE type = 'Follow'
          GROUP BY
                IdOtherUser
          ) F ON USERS.id = F.IdOtherUser

जबकि एक और सबक्वेरी जोड़ने से अधिक जानकारी के लिए आपकी इच्छा का समाधान हो सकता है, आपके डेटा की वृद्धि के अनुपात में समग्र क्वेरी धीमी हो सकती है। एक बार जब आप कार्यक्षमता पर बस गए हैं तो आपको वास्तव में इसकी आवश्यकता हो सकती है कि उन तालिकाओं पर आपको कौन सी अनुक्रमणिका चाहिए। (मेरा मानना ​​है कि आपको उस सलाह के लिए अलग से पूछने की सलाह दी जाएगी, और यदि आप सुनिश्चित करते हैं कि आप 1. अपनी टेबल का पूरा डीडीएल और 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 में SUBSTR () फ़ंक्शन कैसे काम करता है

  2. DECLARE CURSOR FOR पर सिंटैक्स त्रुटि

  3. 2 अलग-अलग डेटाबेस पर 2 टेबल्स को बाएं कैसे जोड़ा जाए?

  4. आपसी मित्र sql एकीकरण जटिल क्वेरी

  5. $wpdb के साथ समान कथन का उपयोग करना-> हैश दिखाने के लिए तैयार करें जहां वाइल्डकार्ड वर्ण हैं