Terjemahan disediakan oleh mesin penerjemah. Jika konten terjemahan yang diberikan bertentangan dengan versi bahasa Inggris aslinya, utamakan versi bahasa Inggris.
Jenis casting di PostgreSQL adalah proses mengubah nilai dari satu tipe data ke tipe data lainnya. PostgreSQL menyediakan cast bawaan untuk banyak konversi umum, tetapi Anda juga dapat membuat cast khusus untuk menentukan bagaimana konversi tipe tertentu harus berperilaku.
Pemeran menentukan cara melakukan konversi dari satu tipe data ke tipe data lainnya. Misalnya, mengubah teks '123' menjadi bilangan bulat123, atau numerik 45.67 menjadi teks. '45.67'
Dimulai dengan 14.20, 15.15, 16.11, 17.7, dan 18.1, Anda dapat menggunakan ekstensi rds_casts untuk menginstal cast tambahan untuk tipe bawaan, sambil tetap dapat membuat gips Anda sendiri untuk jenis kustom.
Topik
Menginstal dan menggunakan ekstensi rds_casts
Untuk membuat rds_casts ekstensi, sambungkan ke sebagai dan jalankan perintah berikut: rds_superuser
CREATE EXTENSION IF NOT EXISTS rds_casts;
Cast yang didukung
Buat ekstensi di setiap database tempat Anda ingin menggunakan cast kustom. Setelah membuat ekstensi, gunakan perintah berikut untuk melihat semua gips yang tersedia:
SELECT * FROM rds_casts.list_supported_casts();
Fungsi ini mencantumkan kombinasi pemeran yang tersedia (tipe sumber, tipe target, konteks paksaan, dan fungsi pemeran). Misalnya, jika Anda ingin membuat text untuk numeric sebagai implicit pemain. Anda dapat menggunakan kueri berikut untuk mengetahui apakah pemeran tersedia untuk dibuat:
SELECT * FROM rds_casts.list_supported_casts() WHERE source_type = 'text' AND target_type = 'numeric'; id | source_type | target_type | qualified_function | coercion_context ----+-------------+-------------+--------------------------------------+------------------ 10 | text | numeric | rds_casts.rds_text_to_numeric_custom | implicit 11 | text | numeric | rds_casts.rds_text_to_numeric_custom | assignment 13 | text | numeric | rds_casts.rds_text_to_numeric_custom | explicit 20 | text | numeric | rds_casts.rds_text_to_numeric_inout | implicit 21 | text | numeric | rds_casts.rds_text_to_numeric_inout | assignment 23 | text | numeric | rds_casts.rds_text_to_numeric_inout | explicit
Ekstensi rds_casts menyediakan dua jenis fungsi konversi untuk setiap pemeran:
-
fungsi _inout - Gunakan mekanisme I/O konversi standar PostgreSQL, berperilaku identik dengan cast yang dibuat dengan metode INOUT
-
_fungsi khusus - Berikan logika konversi yang disempurnakan yang menangani kasus tepi, seperti mengonversi string kosong ke nilai NULL untuk menghindari kesalahan konversi
inoutFungsi mereplikasi perilaku casting asli PostgreSQL, sementara custom fungsi memperluas fungsionalitas ini dengan menangani skenario yang tidak dapat diakomodasi oleh cast INOUT standar, seperti mengonversi string kosong menjadi bilangan bulat.
Membuat atau menjatuhkan gips
Anda dapat membuat dan melepaskan gips yang didukung menggunakan dua metode:
Cast kreasi
Metode 1: Menggunakan perintah CREATE CAST asli
CREATE CAST (text AS numeric) WITH FUNCTION rds_casts.rds_text_to_numeric_custom AS IMPLICIT;
Metode 2: Menggunakan fungsi rds_casts.create_cast
SELECT rds_casts.create_cast(10);
create_castFungsi mengambil ID dari list_supported_casts() output. Metode ini lebih sederhana dan memastikan Anda menggunakan fungsi dan kombinasi konteks yang benar. Id ini dijamin tetap sama di berbagai versi postgres.
Untuk memverifikasi pemeran berhasil dibuat, kueri katalog sistem pg_cast:
SELECT oid, castsource::regtype, casttarget::regtype, castfunc::regproc, castcontext, castmethod FROM pg_cast WHERE castsource = 'text'::regtype AND casttarget = 'numeric'::regtype; oid | castsource | casttarget | castfunc | castcontext | castmethod --------+------------+------------+--------------------------------------+-------------+------------ 356372 | text | numeric | rds_casts.rds_text_to_numeric_custom | i | f
castcontextKolom menunjukkan: e untuk EXPLISIT, a untuk ASSIGNMENT, atau i untuk IMPLISIT.
Menjatuhkan gips
Metode 1: Menggunakan perintah DROP CAST
DROP CAST IF EXISTS (text AS numeric);
Metode 2: Menggunakan fungsi rds_casts.drop_cast
SELECT rds_casts.drop_cast(10);
drop_castFungsi ini mengambil ID yang sama yang digunakan saat membuat pemeran. Metode ini memastikan Anda menjatuhkan pemeran yang tepat yang dibuat dengan ID yang sesuai.
Membuat gips khusus dengan strategi konteks yang tepat
Saat membuat beberapa cast untuk tipe integer, kesalahan ambiguitas operator dapat terjadi jika semua cast dibuat sebagai IMPLISIT. Contoh berikut menunjukkan masalah ini dengan membuat dua cast implisit dari teks ke lebar integer yang berbeda:
-- Creating multiple IMPLICIT casts causes ambiguity postgres=> CREATE CAST (text AS int4) WITH FUNCTION rds_casts.rds_text_to_int4_custom(text) AS IMPLICIT; CREATE CAST postgres=> CREATE CAST (text AS int8) WITH FUNCTION rds_casts.rds_text_to_int8_custom(text) AS IMPLICIT; CREATE CAST postgres=> CREATE TABLE test_cast(col int); CREATE TABLE postgres=> INSERT INTO test_cast VALUES ('123'::text); INSERT 0 1 postgres=> SELECT * FROM test_cast WHERE col='123'::text; ERROR: operator is not unique: integer = text LINE 1: SELECT * FROM test_cast WHERE col='123'::text; ^ HINT: Could not choose a best candidate operator. You might need to add explicit type casts.
Kesalahan terjadi karena PostgreSQL tidak dapat menentukan cast implisit mana yang akan digunakan saat membandingkan kolom integer dengan nilai teks. Baik pemeran implisit int4 dan int8 adalah kandidat yang valid, menciptakan ambiguitas.
Untuk menghindari ambiguitas operator ini, gunakan konteks ASSIGNMENT untuk lebar bilangan bulat yang lebih kecil dan konteks IMPLISIT untuk lebar bilangan bulat yang lebih besar:
-- Use ASSIGNMENT for smaller integer widths CREATE CAST (text AS int2) WITH FUNCTION rds_casts.rds_text_to_int2_custom(text) AS ASSIGNMENT; CREATE CAST (text AS int4) WITH FUNCTION rds_casts.rds_text_to_int4_custom(text) AS ASSIGNMENT; -- Use IMPLICIT for larger integer widths CREATE CAST (text AS int8) WITH FUNCTION rds_casts.rds_text_to_int8_custom(text) AS IMPLICIT; postgres=> INSERT INTO test_cast VALUES ('123'::text); INSERT 0 1 postgres=> SELECT * FROM test_cast WHERE col='123'::text; col ----- 123 (1 row)
Dengan strategi ini, hanya pemeran int8 yang implisit, sehingga PostgreSQL dapat dengan jelas menentukan pemeran mana yang akan digunakan.