Отримання типу даних кожного стовпця з таблиці PostGIS?


9

Мені потрібно отримати типи даних стовпців усіх стовпців у таблиці, включаючи типи геометрії. Що я хотів знати, чи є функція або SQL, яка дає щось подібне:

column_name | data_type
------------+--------------
gid         | integer
descr       | character varying(32)
class       | character varying(10)
area        | double precision
geom        | geometry(Polygon,3763)

З кількох відповідей на stackexchange та gis.stackexchange я знаю, що я можу отримати частину інформації за допомогою наступного запиту:

SELECT 
    g.column_name,
    g.data_type,
    g.character_maximum_length,
    g.udt_name,
    f.type,
    f.srid
FROM 
     information_schema.columns as g JOIN
     geometry_columns AS f 
         ON (g.table_schema = f.f_table_schema and g.table_name = f.f_table_name )
WHERE
    table_schema = 'my_schema_name' and
    table_name = 'my_table_name'

Результат:

column_name | data_type         | character_maximum_length | udt_name | type    | srid
------------+-------------------+--------------------------+----------+---------+------
gid         | integer           |                          |          |         |
descr       | character varying | 32                       |          |         |
class       | character varying | 10                       |          |         |
area        | double precision  |                          |
geom        | USER-DEFINED      |                          | geometry | Polygon | 3763

Але чи існує правильний більш практичний спосіб отримати інформацію у потрібному мені форматі? Або я повинен увійти у "світ" CASE WHENструктур та конкатенації рядків, щоб зібрати всі атрибути стовпців в один стовпець у такому форматі?

Я боюсь, якщо несподіваний тип даних здивує мене необхідністю іншого атрибута з таблиці information_schema.column. Тобто, у прикладі таблиці раніше я не використовував жодного numeric (15,2)типу даних, для якого потрібно було б використовувати інші атрибути (numeric_precision та numeric_scale), які будуть розбиратися CASE WHEN.

Відповіді:


14

Теорія так, хоча ви могли б знайти її дуже складною.

  • Кожна таблиця (виберіть * з pg_class) містить стовпці.
  • Кожен стовпець (виберіть * з pg_attribute) необов'язково має "типовий" номер.
  • Для типів з типовим типом (виберіть * від pg_type) буде функція "Typmodout".
  • Запустивши функцію виведення друку на номер машинопису, повернеться рядок, який можна об'єднати з ім'ям типу, щоб сформувати тип підпису, прочитаного користувачем, який ви використовували (виберіть 'числовий' || numerictypmodout (786441)) (виберіть geography_typmod_out (1107460))

Але, ей, psql генерує потрібні вам рядки, якщо ми подивимось, який SQL він генерує, можливо, відповідь є там.

Звичайно, існує магічна функція, яка приймає друкарський шрифт і друкарський шрифт і повертає магічну струну.

select a.attname, format_type(a.atttypid, a.atttypmod) from pg_attribute a where attname = 'geog';

З приєднанням до pg_class ви зможете отримати цю інформацію за столом.


Я не отримую жодних результатів, where attname = 'geog'але = 'geom'працює. Це дає хороші результати для значень MultiPolygon, Point та MultiPoint, але я не бачу нічого для типів Line або MultiLine. Вони вважаються багатокутниками?
mhkeller

7

Це можна отримати за допомогою простого запиту SQL.

SELECT * from information_schema.columns where table_name='mytablename'


1
Це чудово працює! І ось підказка. Вихід може бути довгим, тому ви, можливо, захочете ввімкнути розширений дисплей на консолі: \pset pagerвимкнути сторінку, а потім \xувімкнути розширений дисплей.
modulitos

7

За допомогою Пола Рамзі я зробив це так:

SELECT a.attname as column_name, format_type(a.atttypid, a.atttypmod) AS data_type
FROM pg_attribute a
JOIN pg_class b ON (a.attrelid = b.relfilenode)
WHERE b.relname = 'my_table_name' and a.attstattarget = -1;

ОНОВЛЕННЯ

Тим часом я створив функцію запиту певного типу даних стовпця

CREATE OR REPLACE FUNCTION "vsr_get_data_type"(_t regclass, _c text)
  RETURNS text AS
$body$
DECLARE
    _schema text;
    _table text;
    data_type text;
BEGIN
-- Prepare names to use in index and trigger names
IF _t::text LIKE '%.%' THEN
    _schema := regexp_replace (split_part(_t::text, '.', 1),'"','','g');
    _table := regexp_replace (split_part(_t::text, '.', 2),'"','','g');
    ELSE
        _schema := 'public';
        _table := regexp_replace(_t::text,'"','','g');
    END IF;

    data_type := 
    (
        SELECT format_type(a.atttypid, a.atttypmod)
        FROM pg_attribute a 
        JOIN pg_class b ON (a.attrelid = b.oid)
        JOIN pg_namespace c ON (c.oid = b.relnamespace)
        WHERE
            b.relname = _table AND
            c.nspname = _schema AND
            a.attname = _c
     );

    RETURN data_type;
END
$body$ LANGUAGE plpgsql;

Використання:

SELECT vsr_get_data_type('schema_name.table_name','column_name')

-1

якщо ви хочете перевірити тип геометрії, ви можете встановити "udt_name" у "INFORMATION_SCHEMA.COLUMNS" і використовувати його !:

select column_name,udt_name, data_type, character_maximum_length from INFORMATION_SCHEMA.COLUMNS where table_name =g

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.