2013-05-09 44 views
35

Có cách nào tiêu chuẩn, trong Python, để bình thường hóa một chuỗi unicode, để nó chỉ hiểu các thực thể unicode đơn giản nhất có thể được sử dụng để biểu diễn nó?Bình thường hóa Unicode

Ý tôi là, thứ gì đó sẽ dịch một chuỗi như ['LATIN SMALL LETTER A', 'COMBINING ACUTE ACCENT'] thành ['LATIN SMALL LETTER A WITH ACUTE']?

Xem mà là vấn đề:

>>> import unicodedata 
>>> char = "á" 
>>> len(char) 
1 
>>> [ unicodedata.name(c) for c in char ] 
['LATIN SMALL LETTER A WITH ACUTE'] 

Nhưng bây giờ:

>>> char = "á" 
>>> len(char) 
2 
>>> [ unicodedata.name(c) for c in char ] 
['LATIN SMALL LETTER A', 'COMBINING ACUTE ACCENT'] 

tôi có thể, tất nhiên, lặp trên tất cả các ký tự và làm thay thế sử dụng, vv, nhưng nó không phải là hiệu quả, và tôi khá chắc chắn tôi sẽ bỏ lỡ một nửa số trường hợp đặc biệt, và làm những sai lầm.

Trả lời

60

Module unicodedata cung cấp một .normalize() function, bạn muốn bình thường hóa với hình thức NFC:

>>> unicodedata.normalize('NFC', u'\u0061\u0301') 
u'\xe1' 
>>> unicodedata.normalize('NFD', u'\u00e1') 
u'a\u0301' 

NFC, hoặc 'Normal Form Gồm' lợi nhuận bao gồm ký tự, NFD, 'Normal Form phân hủy' mang đến cho bạn bị phân hủy, ký tự kết hợp.

Các biểu mẫu NFKC và NFKD bổ sung đối phó với các điểm tương thích; ví dụ. U + 2160 (ROMAN NUMERAL ONE) thực sự giống với U + 0049 (LATIN CAPITAL LETTER I) nhưng có trong tiêu chuẩn Unicode để duy trì tương thích với các mã hóa xử lý chúng một cách riêng biệt. Sử dụng một trong hai NFKC hoặc NFKD hình thức, ngoài việc sáng tác hoặc phân hủy các nhân vật, cũng sẽ thay thế tất cả 'tương thích' nhân vật với hình thức kinh điển của họ:

>>> unicodedata.normalize('NFC', u'\u2167') # roman numeral VIII 
u'\u2167' 
>>> unicodedata.normalize('NFKC', u'\u2167') # roman numeral VIII 
u'VIII' 

Lưu ý rằng không có gì bảo đảm rằng sáng tác và các hình thức phân hủy là giao tiếp; chuẩn hóa một ký tự kết hợp thành dạng NFC, sau đó chuyển đổi kết quả trở lại dạng NFD không phải lúc nào cũng dẫn đến cùng một chuỗi ký tự. Tiêu chuẩn Unicode maintains a list of exceptions; các ký tự trong danh sách này có thể được tổng hợp, nhưng không thể phân tách lại thành dạng kết hợp của chúng, vì nhiều lý do khác nhau. Xem thêm tài liệu trên Composition Exclusion Table.

+0

Trong số các biểu mẫu này, NFC đến gần nhất để đáp ứng yêu cầu “nó chỉ hiểu các thực thể unicode đơn giản nhất có thể được sử dụng để biểu diễn nó” được hiểu là đề cập đến số điểm mã Unicode nhỏ nhất. Tuy nhiên, NFC cũng ảnh hưởng đến những thứ khác, ví dụ: thay thế các ký tự bằng các quy tắc tương đương của chúng. Để thực hiện * chỉ * phần giảm thiểu, tôi e rằng bạn sẽ phải tự mình lập trình. –

Các vấn đề liên quan