Выберите столбцы с определенными именами столбцов в PostgreSQL
Я хочу написать простой запрос, чтобы выбрать количество столбцов в PostgreSQL. Однако я продолжаю получать ошибки - я пробовал несколько вариантов, но они не работали для меня. На данный момент я получаю следующую ошибку:
org.postgresql.util.PSQLException: ОШИБКА: синтаксическая ошибка в или около "столбца"
Чтобы получить столбцы со значениями, я пробую следующее:
select * from weather_data where column like '%2010%'
Есть идеи?
5 ответов
column
это зарезервированное слово. Вы не можете использовать его в качестве идентификатора, если не заключите его в двойные кавычки. Подобно: "column"
,
Это не значит, что ты должен. Только не используйте зарезервированные слова в качестве идентификаторов. Когда-либо.
Чтобы...
выберите список столбцов с 2010 в их названии:
.. вы можете использовать эту функцию для динамического построения команды SQL из таблицы системного каталога pg_attribute:
CREATE OR REPLACE FUNCTION f_build_select(_tbl regclass, _pattern text)
RETURNS text AS
$func$
SELECT format('SELECT %s FROM %s'
, string_agg(quote_ident(attname), ', ')
, $1)
FROM pg_attribute
WHERE attrelid = $1
AND attname LIKE ('%' || $2 || '%')
AND NOT attisdropped -- no dropped (dead) columns
AND attnum > 0; -- no system columns
$func$ LANGUAGE sql;
Вызов:
SELECT f_build_select('weather_data', '2010');
Возвращает что-то вроде:
SELECT foo2010, bar2010_id, FROM weather_data;
Вы не можете сделать это полностью динамическим, потому что возвращаемый тип неизвестен, пока мы не создадим запрос.
Это даст вам список столбцов в конкретной таблице (при необходимости вы можете добавить схему):
SELECT column_name
FROM information_schema.columns
WHERE table_name = 'yourtable'
and column_name like '%2010%'
Затем вы можете использовать этот запрос для создания динамического оператора SQL для возврата ваших результатов.
Попытки использовать такие динамические структуры обычно указывают на то, что вы должны использовать такие форматы данных, как hstore
, json
, xml
и т. д., которые доступны для динамического доступа.
Вы можете получить динамический список столбцов, создав SQL на лету в вашем приложении. Вы можете запросить INFORMATION_SCHEMA
получить информацию о столбцах таблицы и построить запрос.
Это можно сделать в PL/PgSQL и запустить сгенерированный запрос с EXECUTE
но вам будет трудно работать с результатом RECORD
, поскольку вы должны получать и декодировать составные кортежи, вы не можете развернуть результирующий набор в обычный список столбцов. Заметим:
craig=> CREATE OR REPLACE FUNCTION retrecset() returns setof record as $$
values (1,2,3,4), (10,11,12,13);
$$ language sql;
craig=> select retrecset();
retrecset
---------------
(1,2,3,4)
(10,11,12,13)
(2 rows)
craig=> select * from retrecset();
ERROR: a column definition list is required for functions returning "record"
craig=> select (r).* FROM (select retrecset()) AS x(r);
ERROR: record type has not been registered
Все, что вы можете сделать, это получить необработанную запись и декодировать ее в клиенте. Вы не можете индексировать в него из SQL, вы не можете преобразовать его во что-либо еще и т. Д. Большинство клиентских API не предоставляют средств для анализа текстовых представлений анонимных записей, поэтому вам, вероятно, придется написать это самостоятельно.
Итак: вы можете возвращать динамические записи из PL/PgSQL, не зная их типа результата, это просто не особенно полезно, и с клиентской стороной это трудно. Вы действительно хотите просто использовать клиент для генерации запросов.
Вы не можете искать все столбцы, как это. Вы должны указать конкретный столбец.
Например,
select * from weather_data where weather_date like '%2010%'
или еще лучше, если это дата, укажите диапазон дат:
select * from weather_data where weather_date between '2010-01-01' and '2010-12-31'
Нашел это здесь:
SELECT 'SELECT ' || array_to_string(ARRAY(SELECT 'o' || '.' || c.column_name
FROM information_schema.columns As c
WHERE table_name = 'officepark'
AND c.column_name NOT IN('officeparkid', 'contractor')
), ',') || ' FROM officepark As o' As sqlstmt
Результатом является запрос SQL SELECT, который вы просто должны выполнить дальше. Это соответствует моим потребностям, так как я передаю результат в оболочку следующим образом:
psql -U myUser -d myDB -t -c "SELECT...As sqlstm" | psql -U myUser -d myDB
Это возвращает мне форматированный вывод, но он работает только в оболочке. Надеюсь, это поможет кому-нибудь когда-нибудь.