2011-08-25 22 views
9

में अद्यतन रिटर्निंग क्लॉज से चयन नहीं कर सकता है, मैं एक और अधिक जटिल क्वेरी से समस्या को अलग करता हूं। यहाँ परीक्षण परिदृश्यपोस्टग्रेस

DROP TABLE test; 
CREATE TABLE test (
    id integer, 
    description varchar(100) 
); 

INSERT INTO test(id, description) VALUES (1,'new'); 
INSERT INTO test(id, description) VALUES (2,'new'); 

अगर मैं क्वेरी चलाने:

SELECT * FROM test WHERE id IN (UPDATE test set description='test' RETURNING id) 

मैं निम्न त्रुटि हो रही है: पर या निकट "परीक्षण" लाइन 1 सिंटेक्स त्रुटि:

त्रुटि: चयन करें * आईडी से (आईडी परीक्षण परीक्षा विवरण = 'परीक्षण' आरई ... ^

*** Fehler ** *

त्रुटि: पर सिंटेक्स त्रुटि या निकट "परीक्षण" एसक्यूएल स्थिति: 42,601 Zeichen: 37

लेकिन अगर मैं केवल statemennt चलाने

:
UPDATE test set value='test' RETURNING id 

2 पंक्तियों के साथ एक परिणाम मिलता है

मुझे लगता है कि परिणाम substitude अगर मैं की तरह एक प्रश्न होगा:

SELECT * FROM test WHERE id IN (1,2); 
परिणाम के साथ

:

1; "परीक्षण" 2; "परीक्षण"

मुझे अपने शुरुआती वक्तव्य के साथ एक ही परिणाम क्यों नहीं मिलता?

+1

वे अलग बयान होना है। तथ्य यह है कि दो पंक्तियों को अद्यतन किया जा रहा है, यह समस्याएं पैदा करने की संभावना है, कभी भी एक पंक्ति/मूल्य वापस आने पर वापस लौटने की कोशिश नहीं की जाती है। –

उत्तर

23

PostgreSQL 9.1 INSERT/UPDATE/DELETE को केवल शीर्ष स्तर के विवरण के रूप में उपयोग किया जा सकता है। यही कारण है कि आपको एक वाक्यविन्यास त्रुटि मिल रही है।

9.1 से शुरू करना आप सामान्य तालिका अभिव्यक्तियों के साथ डेटा-संशोधित बयान का उपयोग कर सकते हैं।आपकी उदाहरण क्वेरी इस तरह दिखेगी:

WITH updated AS (UPDATE test SET description = 'test' RETURNING id) 
SELECT * FROM test WHERE id IN (SELECT id FROM updated); 

बस संशोधित तालिका से चयन करने से सावधान रहें। आप इस तरह भ्रमित परिणाम प्राप्त कर सकते हैं। प्रश्नों को एक ही स्नैपशॉट में निष्पादित कर दिया गया है, SELECT को अद्यतन विवरण के प्रभाव दिखाई नहीं देंगे।

+2

एफवाईआई, सीटीई दृष्टिकोण आईएनएसईआरटी –

+0

के साथ काम नहीं करता है, इसलिए यह 'चयन' आईडी और पुरानी विवरण मान '' नया 'बदले में अपडेट किए गए मान' test'' 'को वापस कर देगा? – Davos

6

आप अपनी UPDATE क्वेरी में दो पंक्तियां अपडेट करते हैं, प्रभावित पंक्तियों को प्रतिबंधित करने के लिए WHERE खंड जोड़ें।

UPDATE test SET description = 'test' WHERE id = 1 RETURNING id 

एक एकल पंक्ति वापस जाने के लिए।

+0

चुनें * परीक्षण से आईडी (अद्यतन परीक्षण SET मान = 'परीक्षण' जहां आईडी = 1 टर्निंग आईडी) एक ही त्रुटि दिखाता है – markus

+0

"विवरण" को "विवरण" में अपडेट किया गया, एक ही समस्या – markus

3

क्या आप IN: ... WHERE id IN (UPDATE ... खो रहे हैं?

However if I only run the statemennt "UPDATE test set value='test' RETURNING id", I get a result with 2 rows. Why is that?

आपका UPDATE कोई WHERE खंड है और इसलिए यह हर पंक्ति, जिनमें से दो हैं अद्यतन करता है।

+0

हाँ, बस इसे – markus

+0

अपडेट किया गया है अपडेट रिटर्निंग नहीं है, जो क्लॉज के साथ और बिना काम कर रहा है। मुद्दा इसके चारों ओर चयन के साथ है। – markus

1

आप अपने खंड को सीमित नहीं कर रहे हैं। आपको id = (blahblah) या id IN (blahblah)

1
UPDATE test set description='test' RETURNING * 

आपको परिणाम सेट सेट करेगा जो आप प्रारंभिक क्वेरी से अपेक्षा करते हैं।

लेकिन मुझे संदेह है कि आप कुछ और जटिल कोशिश कर रहे थे?

0
DROP TABLE IF EXISTS test_tab; 

CREATE TABLE test_tab (
    id integer, 
    description varchar(100) 
); 

INSERT INTO test_tab(id, description) VALUES (1,'new'); 
INSERT INTO test_tab(id, description) VALUES (2,'new'); 

SELECT * from test_tab; 

DO $$ 
DECLARE 
    myID test_tab.id%TYPE; 
    testID test_tab.id%TYPE; 
    cur_IDs CURSOR for select id from test_tab; 
BEGIN 
    OPEN cur_IDs; 
    LOOP 
     FETCH cur_IDs into testID; 
     EXIT WHEN testID is NULL; 

     UPDATE test_tab SET description='test' WHERE id = testID RETURNING id into myID; 
     raise notice 'myID %', myID; 
    END LOOP; 
    CLOSE cur_IDs; 
END$$; 


DROP TABLE IF EXISTS test_tab; 
-1

मैं, चींटियों आसमा से अतिरिक्त कर रहा हूँ अगर एक ही मेज पर का चयन करें, का उपयोग करते हुए:

WITH updated AS (UPDATE test SET description = 'test' RETURNING id, description) 
SELECT * FROM updated; 
संबंधित मुद्दे