UTF-8 ve Unicode arasındaki fark nedir?


503

Wikipedia UTF-8 sayfasına göre insanlardan çelişkili görüşler duydum .

Onlar aynı şey, değil mi? Birisi açıklığa kavuşturabilir mi?


1
Bu WIKI unicode ve UTF'ler hakkında ne yazıyor bence. Üzerinde bazı yorumlar gariptir: "UTF-8'de (veya başka bir çok baytlı kodlamada) geçersiz bir dizeye neden olabilecek bir karakterin ortasındaki bir dizeyi bölmek veya kısaltmak mümkündür." UTF-8 kodlu bir dize artık bir dize değil, bir bayt dizisi veya bayt akışıdır. Dizeyi oluşturan karakterler kodlanır. Tabii ki de kodu çözülebilir. Şimdi elbette bir başlangıç ​​baytından sonra veya bir sonraki bayttan sonra bir utf-8 dizisini kesebilirsiniz, ancak neden birisi bunu yapmalı?
aydınlık

Dize veri türleri hakkında bu makale eğiticidir : mortoray.com/2013/11/27/the-string-type-is-broken - bazen dizelerle ve bayt seviyesi bileşenleriyle çalışırken, bir karakteri yanlışlıkla ikiye bölebilirsiniz .
Everett

Yanıtlar:


495

Başkalarının verdiği cevapları genişletmek için:

Bilgisayarların ideal olarak göstermesi gereken çok sayıda karakter içeren birçok dilimiz var. Unicode her karaktere benzersiz bir sayı veya kod noktası atar.

Bilgisayarlar bayt gibi sayılarla uğraşıyor ... burada biraz tarih atlıyor ve bellek adresleme sorunlarını görmezden geliyor, 8 bit bilgisayarlar 8 bit bayta donanımda kolayca temsil edilen en büyük sayısal birim gibi davranacak, 16 bit bilgisayarlar genişletilecek iki bayta, vb.

ASCII gibi eski karakter kodlamaları (ön-) 8 bitlik dönemden gelir ve o anda hesaplamadaki baskın dili, yani İngilizce'yi 0 ila 127 (7 bit) arasında rakamlara sıkıştırmaya çalışır. Alfabede 26 harf ile hem büyük hem de büyük olmayan form, sayılar ve noktalama işaretleri oldukça iyi çalıştı. ASCII, İngilizce olmayan diğer diller için 8. bit genişletildi, ancak bu genişletme tarafından sağlanan ek 128 sayı / kod noktası, görüntülenen dile bağlı olarak farklı karakterlerle eşleştirilir. ISO-8859 standartları bu eşlemenin en yaygın biçimleridir; ISO-8859-1 ve ISO-8859-15 (ISO-Latin-1, latin1 olarak da bilinir ve evet 8859 ISO standardının iki farklı sürümü de vardır).

Ancak, birden fazla dilden karakterleri temsil etmek istediğinizde bu yeterli değildir, bu nedenle mevcut tüm karakterleri tek bir bayta sıkıştırmak işe yaramaz.

Temelde iki farklı kodlama türü vardır: biri daha fazla bit ekleyerek değer aralığını genişletir. Bu kodlamalara örnek olarak UCS2 (2 bayt = 16 bit) ve UCS4 (4 bayt = 32 bit) verilebilir. Limit çok daha yüksek olsa bile, değer aralıkları hala sınırlı olduğundan, ASCII ve ISO-8859 standartları ile doğal olarak aynı problemden muzdariptirler.

Diğer kodlama türü karakter başına değişken sayıda bayt kullanır ve bunun için en çok bilinen kodlamalar UTF kodlamalarıdır. Tüm UTF kodlamaları kabaca aynı şekilde çalışır: UTF-8 için 8 bit, UTF-16 için 16 bit ve UTF-32 için 32 bit olan bir birim boyutu seçersiniz. Standart daha sonra bu bitlerden birkaçını bayrak olarak tanımlar: ayarlanmışlarsa, birimler dizisindeki bir sonraki birim aynı karakterin bir parçası olarak kabul edilir. Ayarlanmazlarsa, bu birim bir karakteri tam olarak temsil eder. Bu nedenle, en yaygın (İngilizce) karakterler UTF-8'de yalnızca bir bayt (UTF-16'da iki, UTF-32'de 4), ancak diğer dil karakterleri altı bayt veya daha fazla işgal edebilir.

Çok baytlı kodlamalar (yukarıdaki açıklamadan sonra çok birimli olduğunu söylemeliyim), nispeten yer tasarruflu olma avantajına sahiptir, ancak alt dizeleri, karşılaştırmaları vb. Bu tür işlemlerin gerçekleştirilmesinden önceki noktalar (yine de bazı kısayollar vardır).

Hem UCS standartları hem de UTF standartları, Unicode'da tanımlanan kod noktalarını kodlar. Teoride, bu kodlamalar herhangi bir sayıyı kodlamak için kullanılabilir (kodlamanın desteklediği aralık dahilinde) - ancak elbette bu kodlamalar Unicode kod noktalarını kodlamak için yapıldı. Ve bunlar arasındaki ilişkiniz.

Windows "Unicode" dizelerini UTF-16 dizeleri olarak ele alırken, çoğu UNIX bu günlerde varsayılan olarak UTF-8'i kullanır. HTTP gibi iletişim protokolleri, UTF-8'deki birim boyutu ASCII ile aynı olduğundan ve bu tür protokollerin çoğu ASCII döneminde tasarlandığından, UTF-8 ile en iyi şekilde çalışır. Öte yandan UTF-16, tüm canlı dilleri temsil ederken en iyi ortalama alan / işleme performansını sağlar.

Unicode standardı, 32 bit'te gösterilebilecekden daha az kod noktası tanımlar. Böylece, tüm pratik amaçlar için, UTF-32 ve UCS4 aynı kodlama haline geldi, çünkü UTF-32'deki çok üniteli karakterlerle uğraşmanız pek mümkün değil.

Umarım bazı detayları doldurur.


9
Kavramsal olarak, UCS-2 ve UCS-4 olan karakter setleri , değil karakter kodlamaları (dolayısıyla adı).
Mekanik salyangoz

74
@ Tuukka Bu gönderideki hatalar lejyon. Daha ISO 8859. ASCII sadece 2 sürümlerden daha süslü tırnak yüzde işaretleri, vurgular ve diğer Unicode olan bir sürü gibi şeyler eksik, İngilizce için işe yaramadı vardır değil sadece İngilizce olmayan yaklaşık; İngilizce de ihtiyacı var !! HERHANGİ kodlamada hiçbir kod noktası 4 bayttan fazla yer kaplamıyor ; bu 6 baytlık iş yanlıştır. Herhangi bir Unicode skaler değerini UTF olarak kodlayamazsınız, şöyle diyor: taşıyıcılar ve diğer 66 karakterin hepsi yasaktır. UCS-4 ve UTF-32 aynı değil. Çok birimli UTF-32 yoktur. UTF-16 taklit ettikleri kadar verimli değil - & c & c & c!
tchrist

1
ASCII ayrıca pound işareti £ içermez ve elbette euro simgesi (ASCII'den oldukça genç) içermez.
TRiG

1
@tchrist görünüyor 6 bayt olduğunu vardır sonuçta imkansız değil. Bu bakınız: joelonsoftware.com/articles/Unicode.html orada bir boşluk bırakmayı gelen IS olduğunu belirtmektedir 0x04000000için 0x7FFFFFFFveya ikilik öyle 1111110v 10vvvvvv 10vvvvvv 10vvvvvv 10vvvvvv 10vvvvvv - ve bu gerçekten 6 bayt var. Ancak, makalenin "altı bayt veya daha fazla " kafa karıştırıcı iddia ettiği gibi değil , maksimum 6 bayt IS .
sözdizimi

12
@syntaxerror: "Aslında 2, 3, en fazla 6 bayta kadar kod 128 ve üstü kaydedilir." yazıldığında doğruydu, ancak aynı yıl (on iki yıl önce) geçersiz kılındı. tr.wikipedia.org/wiki/UTF-8 "Orijinal şartname 31 bite kadar olan sayıları kapsar (Evrensel Karakter Kümesinin orijinal sınırı). Kasım 2003'te UTF-8, RFC 3629 tarafından U + 'da bitmek üzere kısıtlandı 10FFFF, UTF-16 karakter kodlamasının kısıtlamalarına uymak için. Bu, 5 ve 6 baytlık dizilerin tümünü ve 4 baytlık dizilerin yaklaşık yarısını kaldırdı. "
Mooing Ördek

237

Bu konuyu açıklamak için bir örnek kullanayım:

A chinese character:      汉
it's unicode value:       U+6C49
convert 6C49 to binary:   01101100 01001001

Şu ana kadar büyülü bir şey yok, çok basit. Şimdi bu karakteri sabit diskimizde saklamaya karar verdiğimizi varsayalım. Bunu yapmak için karakteri ikili biçimde kaydetmemiz gerekir. Sadece '01101100 01001001' gibi saklayabiliriz. Bitti!

Ama bir dakika, '01101100 01001001' bir karakter mi yoksa iki karakter mi? Bunun bir karakter olduğunu biliyordunuz çünkü size söyledim, ancak bir bilgisayar okuduğunda hiçbir fikri yoktur. Bu yüzden bilgisayara bir tane gibi davranmasını söylemek için bir çeşit "kodlama" lazım.

'UTF-8'in kuralları burada devreye girer: http://www.fileformat.info/info/unicode/utf8.htm

Binary format of bytes in sequence

1st Byte    2nd Byte    3rd Byte    4th Byte    Number of Free Bits   Maximum Expressible Unicode Value
0xxxxxxx                                                7             007F hex (127)
110xxxxx    10xxxxxx                                (5+6)=11          07FF hex (2047)
1110xxxx    10xxxxxx    10xxxxxx                  (4+6+6)=16          FFFF hex (65535)
11110xxx    10xxxxxx    10xxxxxx    10xxxxxx    (3+6+6+6)=21          10FFFF hex (1,114,111)

Yukarıdaki tabloya göre, eğer 'UTF-8' biçimini kullanarak bu karakteri saklamak istiyorsak, karakterimizin önüne bazı 'başlıklar' koymamız gerekir. Çince karakterimiz 16 bit uzunluğundadır (ikili değeri kendiniz sayın), bu nedenle yeterli alan sağladığı için 3. satırdaki biçimi kullanacağız:

Header  Place holder    Fill in our Binary   Result         
1110    xxxx            0110                 11100110
10      xxxxxx          110001               10110001
10      xxxxxx          001001               10001001

Sonucu bir satırda yazmak:

11100110 10110001 10001001

Bu çince karakterin UTF-8 (ikili) değeridir! (kendiniz onaylayın: http://www.fileformat.info/info/unicode/char/6c49/index.htm )

özet

A chinese character:      汉
it's unicode value:       U+6C49
convert 6C49 to binary:   01101100 01001001
embed 6C49 as UTF-8:      11100110 10110001 10001001

Not: Bu konuyu python'da öğrenmek istiyorsanız, buraya tıklayın


6
"Ama bir dakika, '01101100 01001001' bir karakter mi yoksa iki karakter mi? Bunun bir karakter olduğunu biliyordun, çünkü sana söyledim, ama bir bilgisayar okuduğunda hiçbir fikrim yok. Yani bir çeşit" kodlamaya "ihtiyacımız var. bilgisayara bir tane gibi davranmasını söyle. " Peki tamam, ama bilgisayar hala utf-8 ile kodlamak gerektiğini bilmiyor mu?
Koray Tugay

15
@KorayTugay Bilgisayar hangi kodlamayı kullanması gerektiğini bilmiyor. Bir karakteri bir dosyaya kaydettiğinizde ve ayrıca bir dosyadan bir karakter okuduğunuzda bunu söylemelisiniz.
Cheng

3
@Connor Bilgisayar hangi formatın kullanılacağını bilmiyor. Belgeyi kaydettiğinizde, metin düzenleyicinin kodlamasını açıkça utf-8 veya kullanıcının kullanmak istediği herhangi bir biçim olarak ayarlaması gerekir. Ayrıca, bir metin düzenleyici programı bir dosyayı okuduğunda, kodu doğru şekilde çözmek için bir metin kodlama şeması seçmesi gerekir. Bir harf yazarken ve girerken de aynı şey geçerlidir, metin düzenleyicinin hangi düzeni kullandığınızı bilmesi gerekir, böylece doğru şekilde kaydeder.
Cheng

2
Peki bu başlıklar nasıl yorumlanıyor? Eğer ilk tabloya bakarsanız, bence: bayt bit ile başlarsa 0, karakter 1 ısırıkla (mevcut olan) temsil edilir, bayt ile başlarsa 110, karakter 2 bayt (mevcut ve bir sonraki ( kalan bit 10))), bayt ile başlıyorsa 1110karakter 3 bayt, geçerli ve sonraki 2 bayt (sonra kalan bit 10) ile temsil edilir.
JBoy

2
UTF-8 ile ilgili 10 makaleyi okuyun; bunu okuduktan sonra 10 saniye içinde anladım :)
jrhee17 11:18

201

"Unicode" maalesef bağlama bağlı olarak çeşitli şekillerde kullanılmaktadır. En doğru kullanımı (IMO) kodlanmış bir karakter seti gibidir - yani bir karakter seti ve karakterleri ve bunları temsil eden tamsayı kod noktaları arasında bir eşleme .

UTF-8 bir karakter kodlamasıdır - bayt dizilerinden karakter dizilerine dönüştürmenin bir yolu ve tersi. Unicode karakter kümesinin tamamını kapsar. ASCII karakter başına tek bir bayt olarak kodlanır ve diğer karakterler tam kod noktalarına bağlı olarak daha fazla bayt alır (şu anda tanımlanmış tüm kod noktaları için 4 bayta kadar, yani U-0010FFFF'a kadar ve gerçekten de 4 bayt, U 001FFFFF).

"Unicode" bir karakter kodlamasının adı olarak kullanıldığında (örn. .NET Encoding.Unicode özelliği olarak), genellikle en yaygın karakterleri iki bayt olarak kodlayan UTF-16 anlamına gelir . Bazı platformlar (özellikle .NET ve Java) UTF-16'yı "yerel" karakter kodlaması olarak kullanır. Bu, tek bir UTF-16 değerinde kodlanamayan karakterler hakkında endişelenmeniz gerektiğinde tüylü sorunlara yol açar ("yedek çiftler" olarak kodlanırlar) - ancak çoğu geliştirici bunun için endişelenmez, IME.

Unicode ile ilgili bazı referanslar:


16
Bence UTF-16 sadece Windows platformlarında "Unicode" a eşit. İnsanlar varsayılan olarak * nix'te UTF-8 kullanma eğilimindedir. +1 olsa da, iyi cevap
jalf

10
@Chris: Hayır, ISO-8859-1 UTF-8 değildir . UTF-8, U + 0080 ila U + 00FF'yi bir değil iki bayt olarak kodlar. Windows 1252 ve ISO-8859-1 çoğunlukla aynıdır, ancak doğru hatırlıyorsam 0x80 ve 0x99 değerleri arasında farklılık gösterir, burada ISO 8859-1'in bir "deliği" vardır, ancak CP1252 karakterleri tanımlar.
Jon Skeet

13
UTF-16 "Unicode" deme fikri, kafa karıştırıcı olma potansiyeli nedeniyle bana huzursuz bir şekilde oturuyor - bu sadece açıkça bir .NET sözleşmesi olarak belirtilmiş olsa da. UTF-16, Unicode'u temsil etmenin bir yoludur, ancak "Unicode kodlaması" değildir.
thomasrutter

6
@ unwesen: UTF-8'in vekil çiftlerine ihtiyacı yoktur. Sadece aşamalı olarak daha uzun bayt dizileri kullanan BMP olmayan karakterleri temsil eder.
Jon Skeet

5
@RoyiNamir: Evet, "Unicode" maalesef özellikle Windows'da "UTF-16" anlamına gelir.
Jon Skeet

108

Aynı şey değiller - UTF-8, Unicode'u kodlamanın özel bir yoludur.

Uygulamanıza ve kullanmak istediğiniz verilere bağlı olarak seçebileceğiniz birçok farklı kodlama vardır. En yaygın olarak bildiğim kadarıyla UTF-8, UTF-16 ve UTF-32'ler.


10
ancak, bazı editörler dosyayı "Unicode" VEYA "UTF-8" olarak kaydetmeyi önermektedirler. Yani bu durumda bu "Unicode" ile ilgili bahsetmek gerekli olduğuna inanıyorum UTF-16.
serhio

71

Unicode yalnızca kod noktalarını , yani bir karakteri temsil eden bir sayıyı tanımlar . Bu kod noktalarını bellekte nasıl sakladığınız, kullandığınız kodlamaya bağlıdır . UTF-8, diğerlerinin yanı sıra Unicode karakterleri kodlamanın bir yoludur.


2
ancak, bazı editörler dosyayı "Unicode" VEYA "UTF-8" olarak kaydetmeyi önermektedirler. Yani bu durumda bu "Unicode" ile ilgili bahsetmek gerekli olduğuna inanıyorum UTF-16.
serhio

Bir karakteri sunan bir sayı da ASCII yapar.
aydınlık

6
bu sayfadaki cevapların geri kalanına bakmadan önce ve sonra bunu okuyun
Dodgie

33

Unicode , ISO / IEC 10646 ile birlikte bilinen tüm dilleri temsil etmek için gereken tüm mevcut karakterlerin bir üst kümesi olan Evrensel Karakter Kümesi'ni (UCS) tanımlayan bir standarttır .

Unicode , repertuarındaki her karaktere bir Ad ve Sayı ( Karakter Kodu veya Kod Noktası ) atar .

UTF-8 kodlaması , bu karakterleri bilgisayar belleğinde dijital olarak temsil etmenin bir yoludur. UTF-8 her bir kod noktasını sekizli diziye (8 bit bayt) eşler

Örneğin,

UCS Karakteri = Unicode Han Karakteri

UCS kod noktası = U + 24B62

UTF-8 kodlama = F0 A4 AD A2 (altıgen) = 11110000 10100100 10101101 10100010 (depo gözü)


Hayır, UTF-8 yalnızca kod noktalarını 127'den büyük bir diziye eşler. 0 ile 127 arasındaki her şey bir dizi değil, tek bir bayttır. Btw, ASCII ayrıca bir sayıya bir karakterin Adı da atar, bu nedenle Unicode ile aynıdır. Ancak Unicode 127 kod noktasında durmaz ancak 0x10ffff değerine kadar çıkar.
aydınlık

2
@brightly ben farklıyım. Ascii karakterleri gerçekten de tek bir bayt dizisine eşlenir. Ascii karakterleri için kod durumunda 0 olan ilk bit, kaç baytlık - sıfır olduğunu gösterir. http://www.wikiwand.com/en/UTF-8#/Descriptionİlk satıra bir göz atın.
nightlytrails

Benim için bir dizi birden fazla bayttan oluşur. UTF-8 içindeki bir ASCII karakteri olduğu gibi tek bir bayttır, en önemli bit 0'a ayarlanmıştır. 127'den yüksek kod noktaları her zaman bir başlangıç ​​baytına ve bir, iki veya üç takip bayta sahip dizilere ihtiyaç duyar. Öyleyse neden tek bir bayta "dizi" diyesiniz?
brighty

Pek çok ... İngiliz avukatları çoğu kez yazılımda kasıtlı olarak yanlış kullanıldığından şaşkına dönebilirler. Burada da aynı durum geçerli. Bunu tartışabilirsiniz. Ama bu daha net olmayacak.
nightlytrails

1
@brighty Hmmm, Matematikte, 0 elemanlık bir dizi tamam. Burada 1 elemanlık bir dizi de iyidir.
chux - Monica

24

Unicode sadece bu karakter setini kodlamak için bir karakter setini ( UCS ) ve kodlamaları ( UTF ) tanımlayan bir standarttır . Ancak genel olarak Unicode, standart değil karakter kümesine atıfta bulunur.

Oku , Kesinlikle Mutlak Asgari Her Yazılım Geliştirici Olumlu Unicode ve Karakter Kümeleri (No Bahane!) Hakkında bilmeniz gereken ve Unicode In 5 Dakika .


1
@serhio: Biliyorum. Üç farklı UTF-16 kodlaması olmasına rağmen: İki açık UTF-16LE ve UTF-16BE ve endianitenin bir BOM ile belirtildiği örtük UTF-16 .
Gumbo

@ Gumbo: Malzeme listesinin olmaması, farklı bir kodlama anlamına gelmez. Sadece iki kodlama var.
Mooing Ördek

Yukarıdaki blog Stakcoverflow CEO'su tarafından yazılmıştır.
Shailesh Pratapwar

23

Mevcut cevaplar zaten birçok ayrıntıyı açıklıyor, ancak burada en doğrudan açıklama ve örnekle çok kısa bir cevap var.

Unicode, karakterleri kod noktalarıyla eşleyen standarttır .
Her karakterin 9731 gibi bir sayı olan benzersiz bir kod noktası (kimlik numarası) vardır.

UTF-8, olduğu kodlama codepoints arasında.
Tüm karakterleri diskte (dosyada) saklamak için UTF-8, karakterleri en fazla 4 oktete (8 bit diziler) - bayta böler. UTF-8 çeşitli kodlamalardan biridir (verileri temsil etme yöntemleri). Örneğin, Unicode'da (ondalık) kod noktası 9731 , UTF-8'de 3 bayttan oluşan bir kardan adam ( ) temsil eder :E2 98 83

İşte bazı rastgele örneklerle sıralanmış bir liste .


1
Hayır! UTF-8, unicode karakterleri kodlamanın güzel bir yoludur, ancak UTF-16 veya UTF-32'de de kodlayabiliriz. UTF-32 ile DWORD ve kod noktası arasında 1: 1 ilişkimiz var, UTF-16 ile, suretler ve BOM'lar hariç sadece BMP kod noktaları için WORD ve kod noktası arasında 1: 1 ilişkimiz var. UTF-8'de sadece 127'den küçük kod noktaları için bayt ve kod noktası arasında 1: 1 ilişkimiz var.
brighty

5
@brighty: Doğru, ama neden "Hayır!" Ben "UTF-8 birkaç kodlamalardan biridir" yazdı çünkü ayrıca UTF-16 ve UTF-32 vardır.
27.06.2018

16

1. Unicode

Dünyada "$, &, h, a, t,?, 张, 1, =, + ..." gibi birçok karakter var.

Sonra bu karakterlere adanmış bir organizasyon geliyor,

"Unicode" adlı bir standart yaptılar.

Standart aşağıdaki gibidir:

  • her konumun "kod noktası" veya "kod konumu" olarak adlandırıldığı bir form oluşturun.
  • Bütün pozisyonlar U + 0000 ila U + 10FFFF arasındadır;
  • Şimdiye kadar, bazı pozisyonlar karakterlerle doldurulur ve diğer pozisyonlar kaydedilir veya boş bırakılır.
  • Örneğin, "U + 0024" konumu "$" karakteriyle doldurulur.

PS: Tabii ki ISO adı verilen başka bir standart var - "ISO 10646" - neredeyse aynı.

2. UTF-8

Yukarıdaki gibi, U + 0024 sadece bir pozisyon, bu yüzden "$" karakteri için bilgisayara "U + 0024" kaydedemiyoruz.

Bir kodlama yöntemi olmalıdır.

Sonra UTF-8, UTF-16, UTF-32, UCS-2 gibi kodlama yöntemleri gelir.

UTF-8 altında, kod noktası "U + 0024" 00100100'e kodlanır.

00100100, "$" için bilgisayara kaydettiğimiz değerdir.


1
Genel olarak, UTF-8 bugün herkesin kullandığı tek varyanttır.
Rick James

2
ISO 10646, Unicode karakter kümesiyle aynı standarttır. Unicode, karakter kümesi dışında, sıralama kuralları, durumlar vb. Gibi birçok şeyi tanımlar. ISO 10646 yalnızca karakter kümesidir (şu anda 130.000'in üzerinde olan). Unicode Konsorsiyumu ve ISO, yalnızca karakter kümesi ve kodlamaları ile ilgilenen ISO ile birlikte Unicode'u geliştirir ve Unicode ayrıca metin işlemek için karakter özelliklerini ve kurallarını tanımlar.
thomasrutter

12

Gumbo'nun cevabındaki bağlantıları kontrol ettim ve bu şeylerin bir kısmını Stack Overflow'da var etmek için buraya yapıştırmak istedim.

"... Bazı insanlar, Unicode'un her karakterin 16 bit aldığı ve bu nedenle 65.536 olası karakter olduğu 16 bitlik bir kod olduğu yanılgısı altında. Bu aslında doğru değil. Unicode hakkında en yaygın efsane , öyleyse, bunu kötü hissetme.

Aslında, Unicode karakterler hakkında farklı bir düşünme tarzına sahiptir ve Unicode'un bir şeyleri düşünme şeklini anlamalısınız, yoksa hiçbir şey mantıklı olmayacaktır.

Şimdiye kadar, bir harfin diskte veya bellekte saklayabileceğiniz bazı bitlerle eşleştiğini varsaydık:

A -> 0100 0001

Unicode'da bir harf, hala sadece teorik bir kavram olan kod noktası adı verilen bir şeyle eşleşir. Bu kod noktasının bellekte veya diskte nasıl temsil edildiği başka bir hikaye ... "

"... Her alfabedeki her platonik harfe Unicode konsorsiyumu tarafından şu şekilde yazılmış sihirli bir sayı atanır: U + 0639. Bu sihirli sayıya kod noktası denir. U +" Unicode "anlamına gelir ve sayılar onaltılıktır. U + 0639, Arapça Ain harfidir, İngilizce A harfi U + 0041 olur .... "

“... Tamam, diyelim ki bir dizemiz var:

Merhaba

Unicode'da bu beş kod noktasına karşılık gelir:

U + 0048 U + 0065 U + 006C U + 006C U + 006F.

Sadece bir sürü kod puanı. Rakamlar, gerçekten. Bunu bellekte nasıl saklayacağımız veya bir e-posta mesajında ​​nasıl temsil edeceğimiz hakkında henüz bir şey söylemedik ... "

“... Kodlamalar burada devreye giriyor.

İki bayt hakkındaki efsaneye yol açan Unicode kodlaması için ilk fikir, hey, bu sayıları her biri iki baytta saklayalım. Yani Merhaba olur

00 48 00 65 00 6C 00 6C 00 6F

Sağ? Çok hızlı değil! Ayrıca olamazdı:

48 00 65 00 6C 00 6C 00 6F 00? ..."


ASCII'de, bir harf yalnızca unicode'da değil, bir kod noktasına eşlenir.
aydınlık

8

UTF-8 , Unicode metni için olası bir kodlama şemasıdır .

Unicode , 130.000'den fazla karakteri tanımlayan ve her birine sayısal bir kod (bir kod noktası) tahsis eden geniş kapsamlı bir standarttır. Ayrıca bu metnin nasıl sıralanacağı, normalleştirileceği, durumunun nasıl değiştirileceği ve daha fazlası için kurallar tanımlar. Unicode'daki bir karakter, sıfırdan 0x10FFFF'e kadar olan bir kod noktasıyla temsil edilir, ancak bazı kod noktaları ayrılmıştır ve karakterler için kullanılamaz.

Unicode kod noktalarının bir dizesinin ikili akışa kodlanabilmesinin birden fazla yolu vardır. Bunlara "kodlama" denir. En basit kodlama, her kod noktasını 32 bit tamsayı olarak saklayan UTF-32'dir ve her biri 4 bayt genişliğindedir.

UTF-8 başka bir kodlamadır ve UTF-32 ve diğerlerine göre bir dizi avantaj nedeniyle fiili standart haline gelmektedir. UTF-8, tek bayt değerlerin bir sırası olarak kodlar. Her kod noktası, bu bayt değerlerinin değişken sayısını kullanabilir. ASCII aralığındaki kod noktaları, ASCII ile uyumlu olacak şekilde çıplak kodlanmıştır. Bu aralığın dışındaki kod noktaları, bulundukları aralığa bağlı olarak 2, 3 veya 4 değişken sayıda bayt kullanır.

UTF-8 şu özellikler göz önünde bulundurularak tasarlanmıştır:

  • ASCII karakterleri tam olarak ASCII'deki gibi kodlanır, böylece bir ASCII dizesi de geçerli bir UTF-8 dizesi olur.

  • İkili sıralama: Saf bir ikili sıralama kullanarak UTF-8 dizelerinin sıralanması, yine de tüm kod noktalarının sayısal sırada sıralanmasına neden olur.

  • Birden çok bayt gerektiren karakterler ASCII aralığında herhangi bir bayt değeri içermez ve bir kısmının ASCII karakterleri ile karıştırılamayacağını garanti eder. Bu aynı zamanda bir güvenlik özelliğidir.

  • UTF-8 kolayca doğrulanabilir ve bir doğrulayıcı tarafından diğer karakter kodlamalarından ayırt edilebilir. Diğer 8 bitlik veya çok baytlı kodlamalardaki metinler de nadiren UTF-8 olarak doğrulanır.

  • Rasgele erişim: UTF-8 dizesindeki herhangi bir noktada, o konumdaki baytın bir karakterin ilk baytı olup olmadığını söylemek ve ileriye doğru taramaya gerek kalmadan bir sonraki veya geçerli karakterin başlangıcını bulmak mümkündür. veya birkaç bayttan daha fazla geriye veya akışın başlangıcında bir şey okuyun.


Minör Birkaç nokta: [1] Meli değil "gibi bulunmaktadır ASCII karakterleri tam olarak kodlanmıştır ASCII " olarak değiştirilmelidir "Bulundukları tam olarak kodlanmıştır ASCII karakterleri UTF-8 " ? [2] "Unicode'daki kodlar ..." ifadesi belirsiz (bana göre). Şunu mu demek istediniz: "Unicode kod noktaları ..." ?
skomisa

Nokta 1 için @skomisa, ASCII aralığı içindeki karakterlerin kodlanmasının ASCII ve UTF-8 için aynı olduğunu kastediyorum.
thomasrutter

2. nokta için, bu adil bir nokta ve daha net hale getirmek için bunu düzenleyeceğim
thomasrutter

2

Onlar aynı şey, değil mi?

Hayır, değiller.


Başvurduğunuz Wikipedia sayfasının ilk cümlesinin güzel ve kısa bir özet verdiğini düşünüyorum :

UTF-8, Unicode'daki tüm 1.112.064 geçerli kod noktalarını bir ila dört 8 bit bayt kullanarak kodlayabilen değişken genişlikte bir karakter kodlamasıdır.

Detaylandırmak için:

  • Unicode , karakterlerden sayılara, kod noktaları adı verilen bir haritayı tanımlayan bir standarttır (aşağıdaki örnekte olduğu gibi). Tam haritalama için buraya bir göz atabilirsiniz .

    ! -> U+0021 (21),  
    " -> U+0022 (22),  
    \# -> U+0023 (23)
    
  • UTF-8, bu kod noktalarını bilgisayarın anlayabileceği bir formda, diğer bir deyişle bit olarak kodlamanın yollarından biridir . Başka bir deyişle, bu kod noktalarının her birini bir bit dizisine dönüştürmek veya bir bit dizisini eşdeğer kod noktalarına dönüştürmek için bir yol / algoritmadır. Unicode için birçok alternatif kodlama olduğunu unutmayın.


Joel gerçekten güzel bir açıklama ve tarihin bir bakış verir burada .


2

Bu konudan ne topladığımı özetleyebilirsem:

Unicode karakterleri sıralı sayılara 'çevirir' (ondalık biçimde) .

à = 224

UTF-8, bu sayıları ikili gösterimlere 'çeviren' bir kodlamadır .

224 = 11000011 10100000

0b11100000 olan ikili biçiminden değil, 224'ün ikili gösteriminden bahsettiğimizi unutmayın.


2

Bu makalede tüm ayrıntılar açıklanmaktadır http://kunststube.net/encoding/

TAMPON YAZMA

UTF8 kodlamalı bir 4 bayt arabelleğe sembol yazarsanız , ikili kodunuz şöyle görünür:

00000000 11100011 10000001 10000010

UTF16 kodlamalı bir 4 bayt ara belleğe yazarsanız , ikili kodunuz şöyle görünür:

00000000 00000000 00110000 01000010

Gördüğünüz gibi, içeriğinizde hangi dili kullanacağınıza bağlı olarak bu, belleğinizi buna göre etkileyecektir.

Örneğin, bu özel sembol için: UTF16 kodlaması, bir sonraki sembol için 2 yedek baytımız olduğundan daha verimlidir. Ancak bu, Japonya alfabesi için UTF16 kullanmanız gerektiği anlamına gelmez.

TAMPONDAN OKUMA

Şimdi yukarıdaki baytları okumak istiyorsanız, hangi kodlamaya yazıldığını bilmeniz ve doğru bir şekilde kodunu çözmeniz gerekir.

Bu deşifre olursa örneğin: 00000000 11100011 10000001 10000010 UTF16 kodlama içine, sen ile sona erecek değil

Not: Kodlama ve Unicode iki farklı şeydir. Unicode, her sembolün benzersiz bir kod noktasına eşlendiği büyük (tablo) . örneğin sembol (harf) bir (kod noktası) içerir : 30 42 (altıgen). Diğer yandan kodlama, donanıma depolarken sembolleri daha uygun bir biçime dönüştüren bir algoritmadır.

30 42 (hex) - > UTF8 encoding - > E3 81 82 (hex), which is above result in binary.

30 42 (hex) - > UTF16 encoding - > 30 42 (hex), which is above result in binary.

resim açıklamasını buraya girin


çok iyi bağlantılı makale, umarım aktif olmaya devam eder
yolob 21

0

UTF-8 , 8 bit diziler kullanarak Unicode karakterleri kodlamak için bir yöntemdir.

Unicode , birçok dilden çok çeşitli karakterleri temsil etmek için bir standarttır.


4
"8-bit diziler"…? Bunu daha kesin olarak belirtmek isteyebilirsiniz ...
deceze
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.