Sqlserver
 sql >> Cơ Sở Dữ Liệu >  >> RDS >> Sqlserver

Chuyển đổi Unicode sang Không Unicode

Có một số điều cần lưu ý ở đây:

  1. Nếu bạn muốn xem chính xác ký tự ở đó, bạn có thể chuyển đổi giá trị thành VARBINARY sẽ cung cấp cho bạn giá trị hex / nhị phân của tất cả các ký tự trong chuỗi và không có khái niệm về ký tự "ẩn" trong hex:

    DECLARE @PostalCode NVARCHAR(20);
    SET @PostalCode = N'053000'+ NCHAR(0x2008); -- 0x2008 = "Punctuation Space"
    SELECT @PostalCode AS [NVarCharValue],
           CONVERT(VARCHAR(20), @PostalCode) AS [VarCharValue],
           CONVERT(VARCHAR(20), RTRIM(@PostalCode)) AS [RTrimmedVarCharValue],
           CONVERT(VARBINARY(20), @PostalCode) AS [VarBinaryValue];
    

    Lợi nhuận:

    NVarCharValue   VarCharValue   RTrimmedVarCharValue   VarBinaryValue
    053000          053000?        053000?                0x3000350033003000300030000820
    

    NVARCHAR dữ liệu được lưu trữ dưới dạng UTF-16 hoạt động trong bộ 2 byte. Nhìn vào 4 chữ số hex cuối để xem bộ 2 byte ẩn là gì, ta thấy "0820". Vì Windows và SQL Server là UTF-16 Little Endian (tức là UTF-16LE), các byte có thứ tự ngược lại. Lật 2 byte cuối cùng - 0820 - chúng tôi nhận được "2008", là "Dấu cách chấm câu" mà chúng tôi đã thêm qua NCHAR(0x2008) .

    Ngoài ra, xin lưu ý rằng RTRIM không giúp được gì ở đây.

  2. Nói một cách đơn giản, bạn chỉ có thể thay thế dấu chấm hỏi bằng không:

    SELECT REPLACE(CONVERT(VARCHAR(20), [PostalCode]), '?', '');
    
  3. Quan trọng hơn, bạn nên chuyển đổi [PostalCode] trường thành VARCHAR để nó không lưu trữ các ký tự này. Không quốc gia nào sử dụng các chữ cái không được đại diện trong bộ ký tự ASCII và không hợp lệ cho kiểu dữ liệu VARCHAR, ít nhất là theo như tôi đã từng đọc (xem phần dưới cùng để tham khảo). Trên thực tế, những gì được phép là một tập hợp con khá nhỏ của ASCII, có nghĩa là bạn có thể dễ dàng lọc trên đường vào (hoặc chỉ làm tương tự REPLACE như được hiển thị ở trên khi chèn hoặc cập nhật):

    ALTER TABLE [table] ALTER COLUMN [PostalCode] VARCHAR(20) [NOT]? NULL;
    

    Đảm bảo kiểm tra NULL hiện tại / NOT NULL cài đặt cho cột và làm cho nó giống như trong câu lệnh ALTER ở trên, nếu không nó có thể được thay đổi vì giá trị mặc định là NULL nếu không được chỉ định.

  4. Nếu bạn không thể thay đổi giản đồ của bảng và cần thực hiện "làm sạch" dữ liệu xấu định kỳ, bạn có thể chạy như sau:

    ;WITH cte AS
    (
       SELECT *
       FROM   TableName
       WHERE  [PostalCode] <>
                      CONVERT(NVARCHAR(50), CONVERT(VARCHAR(50), [PostalCode]))
    )
    UPDATE cte
    SET    cte.[PostalCode] = REPLACE(CONVERT(VARCHAR(50), [PostalCode]), '?', '');
    

    Xin lưu ý rằng truy vấn trên không hoạt động hiệu quả nếu bảng có hàng triệu hàng. Tại thời điểm đó, nó sẽ cần được xử lý trong các tập hợp nhỏ hơn thông qua một vòng lặp.

Để tham khảo, đây là bài viết trên wikipedia về Mã bưu chính , hiện tại nói rằng các ký tự duy nhất từng được sử dụng là:

Và về kích thước tối đa của trường, đây là Danh sách mã bưu chính của Wikipedia



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Bảng có nhiều cột

  2. Tại sao tôi không thể sử dụng bí danh trong cột đếm (*) và tham chiếu nó trong mệnh đề có?

  3. Cách gửi kết quả truy vấn qua email dưới dạng tệp đính kèm trong SQL Server (T-SQL)

  4. Thay đổi chủ sở hữu bảng

  5. Khi nào tôi nên sử dụng biến bảng so với bảng tạm thời trong máy chủ sql?