우리는 이것에 대해 여러 번 토론했습니다. 정보 스키마는 특정 목적을 수행합니다. 시스템 카탈로그를 둘러 보는 방법을 알고 있다면 IMO가 대부분의 목적에 더 적합 합니다. 시스템 카탈로그는 모든 정보의 실제 소스입니다.
정보 스키마는 쿼리가 시스템 카탈로그를 조회해야하는 복잡한 정도가되면 다른 RDBMS 플랫폼 이식성은 일반적으로 환상 때문에 도움 대부분의 주요 포스트 그레스 버전 이식성과, 뷰를 표준화 제공합니다. 특히, Oracle은 여전히 정보 스키마를 지원하지 않습니다.
정보 스키마의 뷰는 표준을 준수하는 형식을 달성하기 위해 많은 후프를 뛰어 넘어야합니다. 이로 인해 속도가 느려지고 때로는 매우 느립니다. 이러한 기본 개체에 대한 계획과 성능을 비교하십시오.
EXPLAIN ANALYZE SELECT * from information_schema.columns;
EXPLAIN ANALYZE SELECT * from pg_catalog.pg_attribute;
그 차이는 놀랍습니다. 그것은 실제로 당신이 찾고있는 것에 달려 있습니다.
당신의 예
예를 들어 SELECT * from tbl
,이 간단한 테이블에 대해 아래 두 쿼리를 비교하십시오.
CREATE TEMP TABLE foo(
A numeric(12,3)
, b timestamp(0)
);
사용 pg_attribute
:
SELECT attname, format_type(atttypid, atttypmod) AS type
FROM pg_attribute
WHERE attrelid = 'foo'::regclass
AND attnum > 0
AND NOT attisdropped
ORDER BY attnum;
format_type()
모든 수정 자와 함께 전체 유형을 반환합니다.
attname | type
--------+-------------------------------
a | numeric(12,3)
b | timestamp(0) without time zone
또한 캐스트 regclass
는 현재에 따라 테이블 이름을 다소 지능적 으로 해석합니다 search_path
. 이름이 유효하지 않은 경우에도 예외가 발생합니다. 세부:
사용 information_schema.columns
:
SELECT column_name, data_type
FROM information_schema.columns
WHERE table_name = 'foo'
ORDER BY ordinal_position;
정보는 표준화되었지만 불완전합니다 .
column_name | data_type
------------+----------------------------
a | numeric
b | timestamp without time zone
데이터 유형에 대한 전체 정보를 얻으려면 다음 열을 모두 추가로 고려해야합니다.
character_maximum_length
character_octet_length
numeric_precision
numeric_precision_radix
numeric_scale
datetime_precision
interval_type
interval_precision
관련 답변 :
가장 큰 장점 (IMO) 인 장단점 목록 :
정보 스키마 뷰
- 종종 더 단순하다 (의존한다)
- 느린
- 사전 처리, 요구 사항에 맞거나 맞지 않을 수 있음
- 선택적 (사용자에게는 권한이있는 개체 만 표시됨)
- SQL 표준 준수 (일부 주요 RDBMS에 의해 구현 됨)
- 대부분의 주요 Postgres 버전에서 이식 가능
- Postgres에 대한 특정 지식이 필요하지 않습니다
- 식별자는 설명 적이며 길고 때로는 어색합니다.
시스템 카탈로그
- 소스에 더 가깝고 종종 더 복잡합니다 (의존적)
- 빠른
- 완료 (
oid
포함 된 시스템 열 )
- SQL 표준을 준수하지 않음
- 주요 Postgres 버전에서 이식성이 떨어짐 (기본 사항은 변경되지 않음)
- Postgres에 대한보다 구체적인 지식이 필요합니다
- 식별자는 간결하고 설명이 적지 만 편리합니다.
임의 쿼리
쿼리에서 동일한 열 이름 및 유형 목록을 얻으려면 간단한 트릭 을 사용하십시오. 쿼리 출력에서 임시 테이블 을 만든 다음 위와 동일한 기술을 사용하십시오.
LIMIT 0
실제 데이터가 필요하지 않으므로을 추가 할 수 있습니다 .
CREATE TEMP TABLE tmp123 AS
SELECT 1::numeric, now()
LIMIT 0;
개별 열의 데이터 유형을 얻으려면 다음 함수를 사용할 수도 있습니다 pg_typeof()
.
SELECT pg_typeof(1);