जैसा कि @ पावेल ने समझाया, एक रिकॉर्ड को पार करना संभव नहीं है, जैसे आप एक सरणी को पार कर सकते हैं। लेकिन इसके आसपास कई तरीके हैं - आपकी सटीक आवश्यकताओं के आधार पर। अंततः, चूंकि आप एक ही कॉलम में सभी मानों को वापस करना चाहते हैं, इसलिए आपको उन्हें एक ही प्रकार में डालना होगा - text
स्पष्ट सामान्य आधार है, क्योंकि हर प्रकार के लिए एक पाठ प्रतिनिधित्व है।
त्वरित और गंदा
मान लें, आपके पास integer
वाली एक तालिका है , एक text
और एक date
कॉलम।
CREATE TEMP TABLE tbl(a int, b text, c date);
INSERT INTO tbl VALUES
(1, '1text', '2012-10-01')
,(2, '2text', '2012-10-02')
,(3, ',3,ex,', '2012-10-03') -- text with commas
,(4, '",4,"ex,"', '2012-10-04') -- text with commas and double quotes
तब समाधान सरल हो सकता है:
SELECT unnest(string_to_array(trim(t::text, '()'), ','))
FROM tbl t;
पहली दो पंक्तियों के लिए काम करता है, लेकिन पंक्ति 3 और 4 के विशेष मामलों के लिए विफल रहता है।
आप पाठ प्रतिनिधित्व में अल्पविराम के साथ समस्या को आसानी से हल कर सकते हैं:
SELECT unnest(('{' || trim(t::text, '()') || '}')::text[])
FROM tbl t
WHERE a < 4;
यह ठीक काम करेगा - लाइन 4 को छोड़कर जिसमें टेक्स्ट प्रतिनिधित्व में डबल कोट्स हैं। जिन्हें दुगना करके भाग निकले हैं। लेकिन ऐरे कंस्ट्रक्टर को उन्हें \
. से बचने की आवश्यकता होगी . निश्चित नहीं है कि यह असंगति क्यों है...
SELECT ('{' || trim(t::text, '()') || '}') FROM tbl t WHERE a = 4
पैदावार:
{4,""",4,""ex,""",2012-10-04}
लेकिन आपको इसकी आवश्यकता होगी:
SELECT '{4,"\",4,\"ex,\"",2012-10-04}'::text[]; -- works
उचित समाधान
यदि आप कॉलम के नाम पहले से जानते हैं, तो एक साफ समाधान आसान होगा:
SELECT unnest(ARRAY[a::text,b::text,c::text])
FROM tbl
चूंकि आप अच्छी तरह से ज्ञात प्रकार के रिकॉर्ड पर काम करते हैं, इसलिए आप केवल सिस्टम कैटलॉग को क्वेरी कर सकते हैं:
SELECT string_agg(a.attname || '::text', ',' ORDER BY a.attnum)
FROM pg_catalog.pg_attribute a
WHERE a.attrelid = 'tbl'::regclass
AND a.attnum > 0
AND a.attisdropped = FALSE
इसे डायनामिक SQL वाले फ़ंक्शन में रखें:
CREATE OR REPLACE FUNCTION unnest_table(_tbl text)
RETURNS SETOF text LANGUAGE plpgsql AS
$func$
BEGIN
RETURN QUERY EXECUTE '
SELECT unnest(ARRAY[' || (
SELECT string_agg(a.attname || '::text', ',' ORDER BY a.attnum)
FROM pg_catalog.pg_attribute a
WHERE a.attrelid = _tbl::regclass
AND a.attnum > 0
AND a.attisdropped = false
) || '])
FROM ' || _tbl::regclass;
END
$func$;
कॉल करें:
SELECT unnest_table('tbl') AS val
रिटर्न:
val
-----
1
1text
2012-10-01
2
2text
2012-10-02
3
,3,ex,
2012-10-03
4
",4,"ex,"
2012-10-04
यह अतिरिक्त मॉड्यूल स्थापित किए बिना काम करता है। दूसरा विकल्प यह है कि hstore एक्सटेंशन इंस्टॉल करें और इसे @Craig के प्रदर्शन की तरह इस्तेमाल करें।