बाईं ओर का उपयोग करके MySQL में कई तालिकाएँ अद्यतन करें


165

मेरे पास दो टेबल हैं, और एक लेफ्टिनेंट जॉइन में सभी पंक्तियों के लिए T1 में फ़ील्ड अपडेट करना चाहते हैं।

एक आसान उदाहरण के लिए, निम्न परिणाम-सेट की सभी पंक्तियों को अपडेट करें:

SELECT T1.* FROM T1 LEFT JOIN T2 ON T1.id = T2.id WHERE T2.id IS NULL  

MySQL मैनुअल कहा गया है कि:

एकाधिक तालिका अद्यतन कथन किसी भी प्रकार के ज्वाइन का उपयोग कर सकते हैं जैसे कि सेलेक्ट स्टेटमेंट में, जैसे कि LEFT JOIN।

लेकिन मुझे डॉक्यूमेंटेड मल्टीपल-टेबल UPDATE में करने के लिए उचित सिंटैक्स नहीं मिल रहा है।

उचित वाक्यविन्यास क्या है?

जवाबों:


318
UPDATE  t1
LEFT JOIN
        t2
ON      t2.id = t1.id
SET     t1.col1 = newvalue
WHERE   t2.id IS NULL

ध्यान दें कि इसका SELECTउपयोग NOT IN/ NOT EXISTSसिंटैक्स करने के लिए अधिक कुशल होगा :

SELECT  t1.*
FROM    t1
WHERE   t1.id NOT IN
        (
        SELECT  id
        FROM    t2
        )

प्रदर्शन विवरण के लिए मेरे ब्लॉग में लेख देखें:

दुर्भाग्य से, MySQLएक UPDATEबयान में एक उपश्रेणी में लक्ष्य तालिका का उपयोग करने की अनुमति नहीं देता है , यही कारण है कि आपको कम कुशल LEFT JOINसिंटैक्स से चिपके रहने की आवश्यकता होगी ।


यह Oracle में काम नहीं करता है। उस स्थिति में यह पोस्ट देखें ।
जॉन एंडर

क्या हम इसमें एक सीमा जोड़ सकते हैं? जैसे मैं एक बार में सिर्फ 10000 पंक्तियों को अपडेट करना चाहता हूं। अगर मैं सिर्फ LIMIT 10000 जोड़ूँ तो यह मुझे एक त्रुटि कहती है 'गलत का उपयोग और सीमा'
हरिल सतारा

28

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

UPDATE t1
LEFT JOIN
 t2
ON 
 t2.some_id = t1.some_id
LEFT JOIN
 t3 
ON
 t2.t3_id = t3.id
SET 
 t1.new_column = t3.column;

यह उस मामले में उपयोगी होगा जहां आपके पास उपयोगकर्ता और समूह थे, और आप चाहते थे कि उपयोगकर्ता समूह नाम की अपनी विविधता जोड़ने में सक्षम हो, इसलिए मूल रूप से आप मौजूदा समूह के नाम को उस क्षेत्र में आयात करना चाहेंगे जहां उपयोगकर्ता है। इसे संशोधित करने में सक्षम होने जा रहा है।


4
Table A 
+--------+-----------+
| A-num  | text      | 
|    1   |           |
|    2   |           |
|    3   |           |
|    4   |           |
|    5   |           |
+--------+-----------+

Table B
+------+------+--------------+
| B-num|  date        |  A-num | 
|  22  |  01.08.2003  |     2  |
|  23  |  02.08.2003  |     2  | 
|  24  |  03.08.2003  |     1  |
|  25  |  04.08.2003  |     4  |
|  26  |  05.03.2003  |     4  |

मैं टेबल ए के साथ फ़ील्ड टेक्स्ट को अपडेट करूंगा

UPDATE `Table A`,`Table B`
SET `Table A`.`text`=concat_ws('',`Table A`.`text`,`Table B`.`B-num`," from                                           
",`Table B`.`date`,'/')
WHERE `Table A`.`A-num` = `Table B`.`A-num`

और इस परिणाम पर आओ:

Table A 
+--------+------------------------+
| A-num  | text                   | 
|    1   |  24 from 03 08 2003 /  |
|    2   |  22 from 01 08 2003 /  |       
|    3   |                        |
|    4   |  25 from 04 08 2003 /  |
|    5   |                        |
--------+-------------------------+

जहां टेबल बी से केवल एक क्षेत्र स्वीकार किया जाता है, लेकिन मैं इस परिणाम पर आऊंगा:

Table A 
+--------+--------------------------------------------+
| A-num  | text                                       | 
|    1   |  24 from 03 08 2003                        |
|    2   |  22 from 01 08 2003 / 23 from 02 08 2003 / |       
|    3   |                                            |
|    4   |  25 from 04 08 2003 / 26 from 05 03 2003 / |
|    5   |                                            |
+--------+--------------------------------------------+

0
UPDATE `Table A` a
SET a.`text`=(
        SELECT group_concat(b.`B-num`,' from ',b.`date` SEPARATOR ' / ') 
        FROM `Table B` b WHERE (a.`A-num`=b.`A-num`)
)

-1
                DECLARE @cols VARCHAR(max),@colsUpd VARCHAR(max), @query VARCHAR(max),@queryUpd VARCHAR(max), @subQuery VARCHAR(max)
DECLARE @TableNameTest NVARCHAR(150)
SET @TableNameTest = @TableName+ '_Staging';
SELECT  @colsUpd = STUF  ((SELECT DISTINCT '], T1.[' + name,']=T2.['+name+'' FROM sys.columns
                 WHERE object_id = (
                                    SELECT top 1 object_id 
                                      FROM sys.objects
                                     WHERE name = ''+@TableNameTest+''
                                    )
                and name not in ('Action','Record_ID')
                FOR XML PATH('')
            ), 1, 2, ''
        ) + ']'


  Select @queryUpd ='Update T1
SET '+@colsUpd+'
FROM '+@TableName+' T1
INNER JOIN '+@TableNameTest+' T2
ON T1.Record_ID = T2.Record_Id
WHERE T2.[Action] = ''Modify'''
EXEC (@queryUpd)

3
कृपया उत्तर को अधिक उपयोगी बनाने के लिए स्पष्टीकरण जोड़ें!
नेज़रियो
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.