Programmēšana

Padziļināts ieskats Java rakstzīmju tipā

Java 1.1 versija ievieš vairākas klases darbam ar rakstzīmēm. Šīs jaunās klases izveido abstrakciju, lai no platformai raksturīga rakstzīmju vērtību jēdziena pārveidotu par Unicode vērtības. Šajā slejā tiek apskatīts pievienotais un šo rakstzīmju klases pievienošanas motivācija.

Tips char

Varbūt visvairāk ļaunprātīgi izmantotais bāzes tips C valodā ir tips char. The char tips tiek ļaunprātīgi izmantots daļēji, jo tas ir definēts kā 8 biti, un pēdējos 25 gadus 8 biti ir definējuši arī mazāko nedalāmo atmiņas daļu datoros. Apvienojot pēdējo faktu ar to, ka ASCII rakstzīmju kopa tika definēta tā, lai tā ietilptu 7 bitos, char tips padara ļoti ērtu "universālu" tipu. Tālāk, C, rādītājs uz tipa mainīgo char kļuva par universālo rādītāju tipu, jo viss, uz ko varēja atsaukties kā char varētu arī atsaukties kā uz jebkuru citu veidu, izmantojot liešanu.

Programmas izmantošana un ļaunprātīga izmantošana char tips C valodā noveda pie daudzām nesaderībām starp kompilatoru ieviešanu, tāpēc ANSI standartā C tika veiktas divas specifiskas izmaiņas: universālais rādītājs tika definēts no jauna, lai tam būtu tukšuma tips, tādējādi prasot programmētāja skaidru deklarāciju; un rakstzīmju skaitliskā vērtība tika uzskatīta par parakstītu, tādējādi nosakot, kā pret tām izturēsies, ja tās izmantos skaitliskos aprēķinos. Tad astoņdesmito gadu vidū inženieri un lietotāji saprata, ka 8 biti nav pietiekami, lai attēlotu visas rakstzīmes pasaulē. Diemžēl līdz tam laikam C bija tik iesakņojies, ka cilvēki nevēlējās, varbūt pat nespēja mainīt char tips. Tagad zibiet uz priekšu 90. gados, Java agrīnajos sākumos. Viens no daudzajiem Java valodas dizainā noteiktajiem principiem bija tāds, ka rakstzīmes būs 16 biti. Šī izvēle atbalsta Unicode, standarta veids, kā attēlot daudz dažādu rakstzīmju daudzās dažādās valodās. Diemžēl tas arī noteica pamatu dažādām problēmām, kuras tiek novērstas tikai tagad.

Kas vispār ir raksturs?

Es zināju, ka man ir nepatikšanas, kad attapos uzdodot jautājumu: "Nu un kas ir raksturs? "Nu, raksturs ir burts, vai ne? Burtu ķekars veido vārdu, vārdi veido teikumus un tā tālāk. Tomēr realitāte ir tāda, ka attiecības starp rakstzīmes attēlojumu datora ekrānā , sauca to glifs, uz skaitlisko vērtību, kas norāda šo glifu, ko sauc par a koda punkts, vispār nav īsti vienkāršs.

Es uzskatu, ka esmu laimīgs, ka esmu angļu valodas dzimtā valoda. Pirmkārt, tāpēc, ka tā bija ievērojama skaita to cilvēku kopīgā valoda, kuri piedalījās mūsdienu digitālā datora projektēšanā un attīstībā; otrkārt, tāpēc, ka tajā ir salīdzinoši maz glifu. ASCII definīcijā ir 96 izdrukājamas rakstzīmes, kuras var izmantot angļu valodas rakstīšanai. Salīdziniet to ar ķīniešu valodu, kur ir definēti vairāk nekā 20 000 glifu un šī definīcija ir nepilnīga. Kopš agrīnajiem Morzes un Baudo koda pirmsākumiem angļu valodas vispārējā vienkāršība (maz glifu, statistiskā izskata biežums) ir padarījusi to par digitālā laikmeta lingua-franca. Bet, tā kā ir palielinājies to cilvēku skaits, kuri iestājas digitālajā laikmetā, ir pieaudzis arī tas, kurš runā angliski, kas nav dzimtā. Pieaugot skaitam, arvien vairāk cilvēku arvien vairāk nevēlējās pieņemt, ka datori izmanto ASCII un runā tikai angliski. Tas ievērojami palielināja izpratnei nepieciešamo "rakstzīmju" datoru skaitu. Tā rezultātā datoru kodēto glifu skaitam vajadzēja dubultoties.

Pieejamo rakstzīmju skaits dubultojās, kad godājamais 7 bitu ASCII kods tika iekļauts 8 bitu rakstzīmju kodējumā ar nosaukumu ISO Latin-1 (vai ISO 8859_1, "ISO" ir Starptautiskā standartu organizācija). Kā jūs, iespējams, esat apkopojis ar kodēšanas nosaukumu, šis standarts ļāva pārstāvēt daudzas no latīņu valodas atvasinātās valodas, kuras lieto Eiropas kontinentā. Tas, ka tika izveidots standarts, tomēr nenozīmēja, ka tas ir izmantojams. Tajā laikā daudzi datori jau bija sākuši izmantot pārējās 128 "rakstzīmes", kuras zināmā mērā varētu būt pārstāvētas ar 8 bitu rakstzīmi. Divi saglabājušies šo papildu rakstzīmju izmantošanas piemēri ir IBM personālais dators (PC) un visu laiku populārākais datoru terminālis Digital Equipment Corporation VT-100. Pēdējais dzīvo termināļa emulatora programmatūras veidā.

Par faktisko 8 bitu rakstzīmes nāves laiku, bez šaubām, tiks apspriests gadu desmitiem, bet es to piesaistīju Macintosh datora ieviešanai 1984. gadā. Macintosh ieviesa divus ļoti revolucionārus jēdzienus galvenajā skaitļošanā: rakstzīmju fonti, kas tika saglabāti RAM; un WorldScript, kurus varētu izmantot, lai attēlotu rakstzīmes jebkurā valodā. Protams, šī bija vienkārši kopija tam, ko Xerox bija piegādājis savās Dandelion klases mašīnās Star teksta apstrādes sistēmas veidā, taču Macintosh atveda šīs jaunās rakstzīmju kopas un fontus auditorijai, kas joprojām izmantoja "mēms" terminālus. . Pēc iesākšanas dažādu fontu lietošanu nevarēja pārtraukt - tas vienkārši bija pārāk pievilcīgs pārāk daudziem cilvēkiem. 80. gadu beigās spiediens standartizēt visu šo rakstzīmju lietošanu nonāca līdz ar Unicode konsorcija izveidošanu, kas savu pirmo specifikāciju publicēja 1990. gadā. Diemžēl 80. gados un pat 90. gados reizināts rakstzīmju kopu skaits. Ļoti maz inženieru, kas tajā laikā veidoja jaunus rakstzīmju kodus, uzskatīja, ka topošais Unicode standarts ir dzīvotspējīgs, un tāpēc viņi izveidoja savus kodu attēlojumus glifiem. Tāpēc, lai gan Unicode netika pieņemts labi, noteikti pazuda priekšstats, ka bija pieejamas tikai 128 vai ne vairāk kā 256 rakstzīmes. Pēc Macintosh dažādu fontu atbalsts kļuva par obligātu tekstu apstrādes funkciju. Astoņas bitu rakstzīmes izgaist.

Java un Unicode

Es stāstu stāstu 1992. gadā, kad pievienojos Oak grupai (Java valoda tika saukta par ozolu, kad tā pirmo reizi tika izstrādāta) pie Sun. Bāzes tips char tika definēts kā 16 neparakstīti biti, vienīgais neparakstītais tips Java. 16 bitu rakstzīmes pamatojums bija tāds, ka tas atbalstīs jebkuru Unicode rakstzīmju attēlojumu, tādējādi padarot Java piemērotu virkņu attēlošanai jebkurā valodā, kuru atbalsta Unicode. Bet spēja attēlot virkni un spēja to izdrukāt vienmēr ir bijušas atsevišķas problēmas. Ņemot vērā to, ka lielāko daļu pieredzes Oak grupā ieguva Unix sistēmas un Unix atvasinātas sistēmas, visērtākā rakstzīmju kopa atkal bija ISO Latin-1. Turklāt, ņemot vērā grupas Unix mantojumu, Java I / O sistēma lielā mērā tika modelēta pēc Unix straumes abstrakcijas, kurā katru I / O ierīci varēja attēlot ar 8 bitu baitu plūsmu. Šī kombinācija atstāja kaut ko nepareizu valodā starp 8 bitu ievades ierīci un Java 16 bitu rakstzīmēm. Tādējādi visur, kur Java virknes bija jālasa no 8 bitu straumes vai jāraksta tajā, bija neliels koda gabals, uzlaušana, lai maģiski kartētu 8 bitu rakstzīmes 16 bitu unikodā.

Java Developer Kit (JDK) 1.0 versijās ievades uzlaušana bija DataInputStream klasē, un izvades kapāt bija viss PrintStream klasē. (Patiesībā bija ievades klase ar nosaukumu TextInputStream Java alfa 2 izlaidumā, bet to aizstāja DataInputStream kapāt faktiskajā laidienā.) Tas joprojām rada problēmas iesācējiem Java programmētājiem, jo ​​viņi izmisīgi meklē funkcijas C ekvivalentu Java getc (). Apsveriet šādu Java 1.0 programmu:

importēt java.io. *; public class fiktīvs {public static void main (String args []) {FileInputStream fis; DataInputStream dis; char c; mēģiniet {fis = new FileInputStream ("data.txt"); dis = jauns DataInputStream (fis); while (patiess) {c = dis.readChar (); System.out.print (c); System.out.flush (); ja (c == '\ n') pārtraukums; } fis.close (); } catch (izņēmums e) {} System.exit (0); }} 

No pirmā acu uzmetiena šķiet, ka šī programma atver failu, nolasa to pa vienai rakstzīmei un iziet, kad tiek lasīta pirmā jaunā rinda. Tomēr praksē tas, ko jūs saņemat, ir nevēlama produkcija. Un iemesls, kāpēc jūs saņemat nevēlamu saturu, ir tas readChar skan 16 bitu Unicode rakstzīmes un System.out.print izdrukā, ko tā uzskata par ISO Latin-1 8 bitu rakstzīmēm. Tomēr, ja maināt iepriekš minēto programmu, lai izmantotu readLine funkcija DataInputStream, tas, šķiet, darbojas, jo kods ir readLine lasa formātu, kas tiek definēts ar pārejošu nodošanu Unicode specifikācijai kā "modificēts UTF-8". (UTF-8 ir formāts, ko Unicode norāda, lai attēlotu Unicode rakstzīmes 8 bitu ievades straumē.) Tātad Java 1.0 situācija ir tāda, ka Java virknes sastāv no 16 bitu Unicode rakstzīmēm, taču ir tikai viena kartēšana, kas kartē ISO Latin-1 rakstzīmes Unicode. Par laimi, Unicode definē koda lapu "0" - tas ir, 256 rakstzīmes, kuru augšējie 8 biti visi ir nulle - lai precīzi atbilstu ISO Latin-1 kopai. Tādējādi kartēšana ir diezgan niecīga, un, kamēr jūs izmantojat tikai ISO Latin-1 rakstzīmju failus, jums nebūs problēmu, kad dati atstāj failu, tos manipulē Java klase un pēc tam pārraksta failā .

Apglabājot ievades pārveidošanas kodu šajās klasēs, radās divas problēmas: ne visas platformas savus daudzvalodu failus glabāja modificētā UTF-8 formātā; un, protams, šajās platformās esošās lietojumprogrammas šajā formā ne vienmēr paredzēja rakstzīmes, kas nav latīņu valodas. Tāpēc ieviešanas atbalsts bija nepilnīgs, un nebija vienkāršu veidu, kā vēlāk izlaidumā pievienot nepieciešamo atbalstu.

Java 1.1 un Unicode

Java 1.1 izlaidums ieviesa pilnīgi jaunu saskarņu kopu rakstzīmju apstrādei, ko sauc Lasītāji un Rakstnieki. Es modificēju klases nosaukumu viltus no augšas uz klasi ar nosaukumu forši. The forši klase izmanto InputStreamReader klases, lai apstrādātu failu, nevis DataInputStream klasē. Pieraksti to InputStreamReader ir jaunā apakšklase Lasītājs klase un System.out tagad ir a PrintWriter objekts, kas ir rakstnieks klasē. Šī piemēra kods ir parādīts zemāk:

importēt java.io. *; public class foršs {public static void main (String args []) {FileInputStream fis; InputStreamReader irs; char c; mēģiniet {fis = new FileInputStream ("data.txt"); irs = jauns InputStreamReader (fis); System.out.println ("Kodēšanas izmantošana:" + irs.getEncoding ()); kamēr (taisnība) {c = (char) irslasīts (); System.out.print (c); System.out.flush (); ja (c == '\ n') pārtraukums; } fis.close (); } catch (izņēmums e) {} System.exit (0); }} 

Galvenā atšķirība starp šo piemēru un iepriekšējo kodu sarakstu ir koda izmantošana InputStreamReader klases, nevis DataInputStream klasē. Vēl viens veids, kā šis piemērs atšķiras no iepriekšējā, ir tas, ka ir papildu rinda, kas izdrukā kodējumu, kuru izmanto InputStreamReader klasē.

Svarīgi ir tas, ka esošais kods, kad tas nav dokumentēts (un šķietami nav saprotams) un iestrādāts getChar metode DataInputStream klase, ir noņemts (faktiski tā lietošana ir novecojusi; tas tiks noņemts nākamajā laidienā). 1.1 versijā Java pārveidošanas mehānisms tagad ir iekapsulēts Lasītājs klasē. Šis iekapsulējums nodrošina iespēju Java klases bibliotēkām atbalstīt daudz dažādu ārpustelpu rakstzīmju, kas nav latīņu rakstzīmes, vienmēr iekšēji izmantojot Unicode.

Protams, tāpat kā sākotnējais I / O apakšsistēmas dizains, lasīšanas klasēm ir simetriski kolēģi, kas veic rakstīšanu. Klase OutputStreamWriter var izmantot, lai rakstītu virknes izejas straumē, klasē BufferedWriter pievieno buferizācijas slāni utt.

Kārpu tirdzniecība vai reāls progress?

Zelta dizaina nedaudz augstais mērķis Lasītājs un rakstnieksklasēm bija jāpieradina tas, kas patlaban ir vienas un tās pašas informācijas pārstāvības standartu hodge-podge, nodrošinot standarta veidu, kā pārveidot uz priekšu un atpakaļ starp mantoto attēlojumu - vai tas būtu Macintosh grieķu vai Windows kirilica - un Unicode. Tātad, Java klasei, kas nodarbojas ar virknēm, nav jāmainās, pārejot no platformas uz platformu. Tas varētu būt stāsta beigas, izņemot to, ka tagad, kad reklāmguvuma kods ir iekapsulēts, rodas jautājums, ko šis kods pieņem.

Pētot šo sleju, man atgādināja slaveno Xerox vadītājas citātu (pirms tas bija Xerox, kad tas bija Haloid uzņēmums) par to, ka kopētājs ir lieks, jo sekretāram bija diezgan viegli ievietot oglekļa papīra gabalu rakstāmmašīnu un izveido dokumenta kopiju, kamēr viņa veidoja oriģinālu. Protams, tas, kas ir acīmredzams, ir tas, ka fotokopēšanas iekārta ir daudz labāka personai, kas saņem dokumentu, nekā personai, kas ģenerē dokumentu. JavaSoft ir parādījis līdzīgu ieskatu par rakstzīmju kodēšanas un dekodēšanas klašu izmantošanu, izstrādājot šo sistēmas daļu.

$config[zx-auto] not found$config[zx-overlay] not found