Các cách không có SQL động
Không có kiểu đúc nào từ số hex trong text
đại diện cho một kiểu số, nhưng chúng ta có thể sử dụng bit(n)
như điểm tham chiếu. Có không có giấy tờ phôi từ chuỗi bit (bit(n)
) sang kiểu số nguyên (int2
, int4
, int8
) - đại diện bên trong là tương thích nhị phân. Trích dẫn Tom Lane:
Điều này dựa trên một số hành vi không có giấy tờ của bộ chuyển đổi đầu vào kiểu bit, nhưng tôi không có lý do gì để mong đợi điều đó sẽ bị hỏng. Một vấn đề có thể lớn hơn là nó yêu cầu PG> =8.3 vì trước đó không có bit textto truyền.
integer
cho tối đa 8 chữ số hex
Có thể chuyển đổi tối đa 8 chữ số hex thành bit(32)
và sau đó bị ép buộc thành integer
(số nguyên 4 byte tiêu chuẩn):
SELECT ('x' || lpad(hex, 8, '0'))::bit(32)::int AS int_val
FROM (
VALUES
('1'::text)
, ('f')
, ('100')
, ('7fffffff')
, ('80000000') -- overflow into negative number
, ('deadbeef')
, ('ffffffff')
, ('ffffffff123') -- too long
) AS t(hex);
int_val
------------
1
15
256
2147483647
-2147483648
-559038737
-1
Postgres sử dụng kiểu số nguyên có dấu, vì vậy số hex trên '7fffffff'
tràn vào số nguyên âm những con số. Đây vẫn là một đại diện hợp lệ, duy nhất nhưng ý nghĩa khác. Nếu điều đó quan trọng, hãy chuyển sang bigint
; xem bên dưới.
Đối với hơn 8 chữ số hex, các ký tự có nghĩa nhỏ nhất (vượt quá bên phải) sẽ bị cắt bớt .
4 bit ở dạng mã hóa chuỗi bit thành 1 chữ số hex . Số hex có độ dài đã biết có thể được truyền sang bit(n)
tương ứng trực tiếp. Ngoài ra, đệm số hex có độ dài không xác định với các số 0 ở đầu (0
) như được minh họa và truyền sang bit(32)
. Ví dụ với 7 chữ số hex và int
hoặc 8 chữ số và bigint
:
SELECT ('x'|| 'deafbee')::bit(28)::int
, ('x'|| 'deadbeef')::bit(32)::bigint;
int4 | int8
-----------+------------
233503726 | 3735928559
bigint
cho tối đa 16 chữ số hex
Có thể chuyển đổi tối đa 16 chữ số hex thành bit(64)
và sau đó bị cưỡng chế thành bigint
(int8
, Số nguyên 8 byte) - lại tràn thành số âm ở nửa trên:
SELECT ('x' || lpad(hex, 16, '0'))::bit(64)::bigint AS int8_val
FROM (
VALUES
('ff'::text)
, ('7fffffff')
, ('80000000')
, ('deadbeef')
, ('7fffffffffffffff')
, ('8000000000000000') -- overflow into negative number
, ('ffffffffffffffff')
, ('ffffffffffffffff123') -- too long
) t(hex);
int8_val
---------------------
255
2147483647
2147483648
3735928559
9223372036854775807
-9223372036854775808
-1
-1
uuid
cho tối đa 32 chữ số hex
The Postgres uuid
kiểu dữ liệu không phải là kiểu số . Nhưng đây là loại hiệu quả nhất trong Postgres tiêu chuẩn để lưu trữ tới 32 chữ số hex, chỉ chiếm 16 byte dung lượng. Có một dàn diễn viên trực tiếp từ text
tới uuid
(không cần bit(n)
như điểm tham chiếu), nhưng chính xác 32 chữ số hex là bắt buộc.
SELECT lpad(hex, 32, '0')::uuid AS uuid_val
FROM (
VALUES ('ff'::text)
, ('deadbeef')
, ('ffffffffffffffff')
, ('ffffffffffffffffffffffffffffffff')
, ('ffffffffffffffffffffffffffffffff123') -- too long
) t(hex);
uuid_val
--------------------------------------
00000000-0000-0000-0000-0000000000ff
00000000-0000-0000-0000-0000deadbeef
00000000-0000-0000-ffff-ffffffffffff
ffffffff-ffff-ffff-ffff-ffffffffffff
ffffffff-ffff-ffff-ffff-ffffffffffff
Như bạn có thể thấy, đầu ra tiêu chuẩn là một chuỗi các chữ số hex với các dấu phân tách điển hình cho UUID.
md5 băm
Điều này đặc biệt hữu ích để lưu trữ băm md5 :
SELECT md5('Store hash for long string, maybe for index?')::uuid AS md5_hash;
md5_hash
--------------------------------------
02e10e94-e895-616e-8e23-bb7f8025da42
Xem:
- Loại dữ liệu tối ưu cho trường MD5 là gì?