unicode wide - 為什麼現代Perl默認避免使用UTF-8?




character in (6)

我想知道為什麼使用Perl構建的大多數現代解決方案默認情況下都不啟用UTF-8

我明白核心Perl腳本存在許多遺留問題,它可能會破壞一些東西。 但是,從我的觀點來看,在21世紀,大型新項目(或者俱有較大觀點的項目)應該從頭開始對其軟件進行UTF-8驗證。 我仍然沒有看到它發生。 例如, Moose啟用嚴格和警告,但不是UnicodeModern::Perl減少了樣板,但沒有UTF-8處理。

為什麼? 在2011年的現代Perl項目中是否有避免使用UTF-8的原因?

評論@ tchrist時間太長,所以我在這裡添加它。

我似乎沒有說清楚。 讓我試著添加一些東西。

特里斯特和我看到的情況非常相似,但我們的結論完全是相反的。 我同意,Unicode的情況很複雜,但這就是為什麼我們(Perl用戶和編碼人員)需要一些使得UTF-8處理像現在一樣容易的層(或雜注)。

Tchrist指出要涵蓋很多方面,我會在幾天甚至幾週內閱讀並思考它們。 不過,這不是我的觀點。 tchrist試圖證明沒有一種方法“啟用UTF-8”。 我沒有那麼多的知識來解決這個問題。 所以,我堅持活著的例子。

我玩了Rakudo ,UTF-8就在我需要的地方 。 我沒有任何問題,它只是工作。 也許在更深的地方有一些限制,但在開始時,我測試的所有產品都按我的預期工作。

這不應該成為現代Perl 5的一個目標嗎? 我更加強調這一點:我並不是建議UTF-8作為核心Perl的默認字符集,我建議可以觸發它來開發項目的人。

另一個例子,但有一個更負面的基調。 框架應該使開發更容易。 幾年前,我嘗試了一些Web框架,但只是拋棄了它們,因為“啟用UTF-8”是如此晦澀難懂。 我沒有找到如何以及在何處掛鉤Unicode支持。 這很耗時間,我發現它很容易走舊路。 現在我在這裡看到有與Mason 2處理同樣問題的賞金: 如何使Mason2 UTF-8變得乾淨? 。 所以,這是一個非常新的框架,但是使用它與UTF-8需要深入的內部知識。 它就像一個巨大的紅色標誌:停下來,不要使用我!

我真的很喜歡Perl。 但處理Unicode是痛苦的。 我仍然發現自己跑在牆上。 有些方法tchrist是正確的,它回答了我的問題:新項目不吸引UTF-8,因為它在Perl 5中太複雜了。


Answers

There's a truly horrifying amount of ancient code out there in the wild, much of it in the form of common CPAN modules. I've found I have to be fairly careful enabling Unicode if I use external modules that might be affected by it, and am still trying to identify and fix some Unicode-related failures in several Perl scripts I use regularly (in particular, iTiVo fails badly on anything that's not 7-bit ASCII due to transcoding issues).


我們都同意,由於很多原因,這是一個困難的問題,但這正是試圖讓每個人都更輕鬆的原因。

CPAN上有一個最近的模塊, utf8::all ,它試圖“打開Unicode,全部”。

正如已經指出的那樣,你不能奇蹟般地讓整個系統(外部程序,外部web請求等)使用Unicode,但我們可以一起工作,製作出能夠使常見問題變得更容易的合理工具。 這就是我們是程序員的原因。

If utf8::all doesn't do something you think it should, let's improve it to make it better. Or let's make additional tools that together can suit people's varying needs as well as possible.

`


While reading this thread, I often get the impression that people are using " UTF-8 " as a synonym to " Unicode ". Please make a distinction between Unicode's "Code-Points" which are an enlarged relative of the ASCII code and Unicode's various "encodings". And there are a few of them, of which UTF-8, UTF-16 and UTF-32 are the current ones and a few more are obsolete.

Please, UTF-8 (as well as all other encodings ) exists and have meaning in input or in output only. Internally, since Perl 5.8.1, all strings are kept as Unicode "Code-points". True, you have to enable some features as admiringly covered previously.


I think you misunderstand Unicode and its relationship to Perl. No matter which way you store data, Unicode, ISO-8859-1 , or many other things, your program has to know how to interpret the bytes it gets as input (decoding) and how to represent the information it wants to output (encoding). Get that interpretation wrong and you garble the data. There isn't some magic default setup inside your program that's going to tell the stuff outside your program how to act.

You think it's hard, most likely, because you are used to everything being ASCII. Everything you should have been thinking about was simply ignored by the programming language and all of the things it had to interact with. If everything used nothing but UTF-8 and you had no choice, then UTF-8 would be just as easy. But not everything does use UTF-8. For instance, you don't want your input handle to think that it's getting UTF-8 octets unless it actually is, and you don't want your output handles to be UTF-8 if the thing reading from them can handle UTF-8. Perl has no way to know those things. That's why you are the programmer.

I don't think Unicode in Perl 5 is too complicated. I think it's scary and people avoid it. There's a difference. To that end, I've put Unicode in Learning Perl, 6th Edition , and there's a lot of Unicode stuff in Effective Perl Programming . You have to spend the time to learn and understand Unicode and how it works. You're not going to be able to use it effectively otherwise.


🌴🐪🐫🐪🐫🐪🌞𝕲𝖔𝖆𝖓𝖉𝕯𝖔𝕷𝖎𝖐𝖊𝖜𝖎𝖘𝖊🌞🐪🐫🐪🐁

𝓔𝓭𝓲𝓽:𝙎𝙞𝙢𝙥𝙡𝙚𝙨𝙩℞:𝟕𝘿𝙞𝙨𝙘𝙧𝙚𝙩𝙚𝙍𝙚𝙘𝙤𝙢𝙢𝙚𝙣𝙙𝙖𝙩𝙞𝙤𝙣𝙨

  1. 將您的PERL_UNICODE變量設置為AS 。 這使得所有Perl腳本將@ARGV解碼為UTF-8字符串,並將stdin,stdout和stderr全部三個編碼設置為UTF-8。 這些都是全球效應,而不是詞彙效應。

  2. 在源文件的頂部(程序,模塊,庫,hickey),突出聲明您正在運行perl版本5.12或更高版本,方法如下:

    use v5.12; # minimal for unicode string feature

    use v5.14; # optimal for unicode string feature

  3. 啟用警告,因為先前的聲明只啟用狹窄和功能,而不是警告。 我還建議將Unicode警告提升為例外,所以請使用這兩行,而不僅僅是其中之一。 但請注意,在v5.14版本中, utf8警告類包含三個可單獨啟用的其他子警告: noncharsurrogatenon_unicode 。 這些你可能希望施加更大的控制權。

    use warnings;

    use warnings qw( FATAL utf8 );

  4. 聲明這個源單元被編碼為UTF-8。 雖然曾經有一段時間,這個雜注做了其他的事情,但它現在單獨服務於這個唯一的目的,而不是其他的目的:

    use utf8;

  5. 聲明在這個詞法範圍內打開一個文件句柄的任何東西, 但在其他地方都不是,假定該流以UTF-8編碼,除非另有說明。 這樣你就不會影響其他模塊或其他程序的代碼。

    use open qw( :encoding(UTF-8) :std );

  6. 通過\N{CHARNAME}啟用指定的字符。

    use charnames qw( :full :short );

  7. 如果你有一個DATA句柄,你必須明確地設置它的編碼。 如果你想這是UTF-8,那麼說:

    binmode(DATA, ":encoding(UTF-8)");

當然,你最終可能會發現自己關心的其他事情並沒有結束,但這些足以逼近國家的目標,即“讓所有事情都能用UTF-8工作”,儘管這些條款有點弱化了。

另一個編譯指示,儘管它不是與Unicode相關的,但是:

      use autodie;

強烈建議。

🎅𝕹𝖔𝕸𝖆𝖌𝖎𝕭𝖚𝖑𝖑𝖊𝖙🎅🎅

說“Perl應該[ 某種程度上! ]在默認情況下啟用Unicode“甚至不會開始思考如何在某種罕見和孤立的情況下說出足夠的有用信息。 Unicode不僅僅是一個更大的字符集; 這也是這些角色如何以許多方式相互作用的方式。

即使是(一些)人認為他們想要的簡單的微小措施,也肯定會破壞數百萬行代碼,而這些代碼無法“升級”到你的新的勇敢的新世界現代性。

這是比人們假裝更複雜的方式。 在過去的幾年裡,我一直在想這個問題。 我很樂意證明我錯了。 但我不認為我是。 Unicode基本上比你想強加給它的模型複雜得多,而且在這裡你可以永遠不會在地毯下掃蕩。 如果你嘗試,你會破壞你自己的代碼或其他人的代碼。 在某些時候,你只需要分解並了解Unicode的含義。 你不能假裝它不是。

🐪使Unicode變得簡單,遠遠超過我曾經使用過的其他任何東西。 如果您認為這樣做不好,請嘗試其他方法。 然後回到🐪:要么你會回到一個更美好的世界,否則你會把同樣的知識帶給你,這樣我們就可以利用你的新知識來使這些東西變得更好。

💡𝕴𝖉𝖊𝖆𝖘𝖋𝖔𝖗𝖆⸗𝕬𝖜𝖆𝖗𝖊🐪𝕷𝖆𝖚𝖓𝖉𝖗𝖞𝕷𝖎𝖘𝖙💡

至少,這裡有一些東西似乎需要🐪才能“默認啟用Unicode”,正如您所說的那樣:

  1. 所有🐪源代碼默認應該是UTF-8。 你可以use utf8export PERL5OPTS=-Mutf8

  2. 🐪DATA句柄應該是UTF-8。 您必須按照每個包的方式執行此操作,例如binmode(DATA, ":encoding(UTF-8)")

  3. 對於腳本程序的參數默認應該被理解為UTF-8。 export PERL_UNICODE=Aperl -CA export PERL5OPTS=-CA ,或export PERL5OPTS=-CA

  4. 標準輸入,輸出和錯誤流應該默認為UTF-8。 export PERL_UNICODE=S對於它們中的一些,或者IO和/或E 這就像perl -CS

  5. 除非另有聲明,否則由opened開啟的任何其他手柄應視為UTF-8; export PERL_UNICODE=D或與io特定的這些; export PERL5OPTS=-CD將起作用。 這使得所有這些都成為-CSAD

  6. 覆蓋兩個基數加上你用export PERL5OPTS=-Mopen=:utf8,:std打開的所有數據流export PERL5OPTS=-Mopen=:utf8,:std 。 見uniquote

  7. 你不想錯過UTF-8編碼錯誤。 嘗試export PERL5OPTS=-Mwarnings=FATAL,utf8 。 並確保你的輸入流總是binmode d :encoding(UTF-8) ,而不僅僅是:utf8

  8. 應該將128-255之間的代碼點理解為相應的Unicode代碼點,而不僅僅是未經過驗證的二進制值。 use feature "unicode_strings"export PERL5OPTS=-Mfeature=unicode_strings 。 這將使uc("\xDF") eq "SS""\xE9" =~ /\w/ 。 一個簡單的export PERL5OPTS=-Mv5.12或更好也會得到。

  9. 已命名的Unicode字符默認情況下未啟用,因此請添加export PERL5OPTS=-Mcharnames=:full,:short,latin,greek或其他。 請參閱uninamestcgrep

  10. 您幾乎總是需要從標準Unicode::Normalize模塊的各種類型的分解中訪問函數。 export PERL5OPTS=-MUnicode::Normalize=NFD,NFKD,NFC,NFKD ,然後通過NFD和NFC出站物品始終運行傳入的內容。 這些還沒有我知道的I / O層,但是請參閱nfcnfdnfkdnfkc

  11. 使用eqnelccmpsort和&c&cc的字符串比較總是錯誤的。 因此,而不是@a = sort @b ,您需要@a = Unicode::Collate->new->sort(@b) 。 不妨將其添加到您的export PERL5OPTS=-MUnicode::Collate 。 您可以緩存二進制比較的密鑰。

  12. 🐪像printfwrite這樣的內置插件使用Unicode數據來做錯誤的事情。 您需要為前者使用Unicode::GCString模塊 ,並且還要為後者使用Unicode::LineBreak模塊 。 見uwcunifmt

  13. 如果你想讓它們算作整數,那麼你將不得不通過Unicode::UCD::num函數運行你的\d+捕獲,因為內置的atoi (3)目前還不夠聰明。

  14. 您將在文件系統上遇到文件系統問題。 一些文件系統默默執行到NFC的轉換; 其他人默默執行到NFD的轉換。 其他人還在做其他事情。 有些人甚至完全忽視這個問題,導致更大的問題。 所以你必須做你自己的NFC / NFD處理來保持理智。

  15. 你所有的代碼都涉及到azAZ必須修改 ,包括m//s///tr/// 。 它應該脫穎而出,因為你的代碼被破壞了,成為尖叫的紅旗。 但不清楚它是如何改變的。 獲得正確的財產,並理解他們的案例,比你想像的更難。 我每天都會使用unipropsuniprops

  16. 使用\p{Lu}代碼與使用[A-Za-z]代碼幾乎一樣錯誤。 您需要使用\p{Upper} ,並知道原因。 是, \p{Lowercase}\p{Lower}\p{Ll}\p{Lowercase_Letter}

  17. 使用[a-zA-Z]的代碼更糟糕。 它不能使用\pL\p{Letter} ; 它需要使用\p{Alphabetic} 。 不是所有的字母都是字母,你知道!

  18. 如果您正在使用/[\$\@\%]\w+/查找變量,那麼您遇到了問題。 您需要查找/[\$\@\%]\p{IDS}\p{IDC}*/ ,甚至不會考慮標點符號變量或程序包變量。

  19. 如果您正在檢查空格,那麼您應該根據\h\v選擇。 而且你不應該使用\s ,因為它不代表 [\h\v] ,與普遍的看法相反。

  20. 如果您使用\n作為界限,甚至\r\n ,那麼您做錯了。 你必須使用\R ,這是不一樣的!

  21. 如果你不知道什麼時候以及是否調用Unicode::Stringprep ,那麼你最好學習。

  22. 不區分大小寫的比較需要檢查兩個事物是否是相同的字母,不管它們的變音符號等。 最簡單的方法是使用標準的Unicode :: Collat​​e模塊。 Unicode::Collate->new(level => 1)->cmp($a, $b) 。 還有eq方法等等,你也許應該了解matchsubstr方法。 這些內置插件具有明顯的優勢。

  23. 有時候這還不夠,你需要Unicode :: Collat​​e :: Locale模塊來代替Unicode::Collate::Locale->new(locale => "de__phonebook", level => 1)->cmp($a, $b)代替。 考慮到Unicode::Collate::->new(level => 1)->eq("d", "ð")是true,但是Unicode::Collate::Locale->new(locale=>"is",level => 1)->eq("d", " ð")是錯誤的。 同樣,如果您不使用語言環境,或者使用英語語言,但“ae”和“æ”是eq ,但它們在冰島語區域中不同。 怎麼辦? 這很難,我告訴你。 你可以玩unifmt來測試其中的一些東西。

  24. 考慮如何匹配字符串“ niño ”中的模式CVCV(輔音,元音,輔音,元音)。 它的NFD形式 - 你已經記得更好 - 記得放進去 - 變成“nin'oo”。 現在你要做什麼? 即使假裝元音是[aeiou] (順便說一句,這是錯誤的),你也將無法做類似(?=[aeiou])\X)事情,因為即使在NFD中, ø' 不分解 ! 然而,它會使用我剛剛給你看的UCA比較來測試等於'o'。 你不能依靠NFD,你必須依靠UCA。

💩𝔸𝕤𝕤𝕦𝕖𝕖𝔹𝕠𝕜𝕖𝕟𝕖𝕖𝕤𝕤💩💩

而這還不是全部。 人們對Unicode有幾百萬個錯誤的假設。 在他們理解這些事情之前,他們的密碼將被破壞。

  1. 假定它可以打開文本文件而不指定編碼的代碼已損壞。

  2. 假定默認編碼的代碼是某種本地平台編碼已被破壞。

  3. 假定日文或中文網頁佔用UTF-16空間少於UTF-8的代碼是錯誤的。

  4. 假設Perl在內部使用UTF-8的代碼是錯誤的。

  5. 假定編碼錯誤總會引發異常的代碼是錯誤的。

  6. 假設Perl代碼點限於0x10_FFFF的代碼是錯誤的。

  7. 假設您可以將$/設置$/適用於任何有效行分隔符的代碼是錯誤的。

  8. 假設循環平等的代碼,如lc(uc($s)) eq $suc(lc($s)) eq $s ,是完全破碎和錯誤的。 考慮到uc("σ")uc("ς")都是"Σ" ,但lc("Σ")不可能返回這兩者。

  9. 假定每個小寫代碼點都有一個明確的大寫字母的代碼被破壞,反之亦然。 例如, "ª"是一個不帶大寫的小寫字母; 而"ᵃ""ᴬ"都是字母,但不是小寫字母; 但是,它們都是小寫代碼點,沒有相應的大寫版本。 了解? 它們不是 \p{Lowercase_Letter} ,儘管它們都是\p{Letter}\p{Lowercase} \p{Letter} \p{Lowercase}

  10. 假定更改大小寫的代碼不會更改字符串的長度被破壞。

  11. 假定只有兩種情況的代碼被破壞。 還有titlecase。

  12. 只承擔字母的代碼有問題。 除了字母之外,事實證明,數字,符號,甚至標記都有案例。 事實上,改變案例甚至可以改變其主要的一般類別,例如\p{Mark}變成\p{Letter} 。 它也可以使它從一個腳本切換到另一個腳本。

  13. 假定這種情況從不依賴於語言環境的代碼被破壞。

  14. 假定Unicode的代碼給出了有關POSIX語言環境的圖。

  15. 假設您可以刪除變音符以獲取基本ASCII字母的代碼是邪惡的,仍然是殘破的,腦殘的,錯誤的,並且是對死刑的理由。

  16. 假定變音符號\p{Diacritic}\p{Mark}是相同的東西的代碼被破壞了。

  17. 假設\p{GC=Dash_Punctuation}代碼與\p{Dash}中斷一樣多。

  18. 假設短劃線,連字符和負數的代碼是彼此相同的東西,或者每個代碼中只有一個是錯誤的。

  19. 假定每個代碼點佔用不超過一個打印列的代碼被破壞。

  20. 假定所有\p{Mark}字符佔用零個打印列的代碼已損壞。

  21. 假設看起來相似的字符相同的代碼被破壞了。

  22. 假定相似的角色相似的代碼被破壞。

  23. 假定只有一個\X可匹配的代碼點數量有限的代碼是錯誤的。

  24. 假定\X無法以\p{Mark}字符開頭的代碼是錯誤的。

  25. 假定\X永遠不能擁有兩個非\p{Mark}字符的代碼是錯誤的。

  26. 假定它不能使用"\x{FFFF}"是錯誤的。

  27. 假定非BMP代碼點需要兩個UTF-16(代理)代碼單元的代碼將編碼為兩個單獨的UTF-8字符,每個代碼單元一個字符是錯誤的。 它不會:它編碼為單碼點。

  28. 如果在產生的UTF-8的開始處放置BOM,那麼從UTF-16或帶有領先BOM的UTF-32轉碼為UTF-8的代碼會被破壞。 這是如此愚蠢的工程師應該刪除他們的眼皮。

  29. 假定CESU-8是有效的UTF編碼的代碼是錯誤的。 同樣,認為將U + 0000編碼為"\xC0\x80"是UTF-8也是錯誤的。 這些傢伙也值得眼瞼治療。

  30. 假定字符如>代碼總是指向右側,並且<始終指向左側是錯誤的 - 因為它們實際上不是。

  31. 如果您首先輸出字符X然後輸出字符Y ,那麼這些代碼會顯示為XY是錯誤的代碼。 有時候他們沒有。

  32. 假設ASCII能夠正確寫英文的代碼是愚蠢的,短視的,文盲,破碎的,邪惡的和錯誤的。 與他們的頭! 如果這看起來太過於極端,我們可以妥協:從今以後,他們只能用一隻腳的大腳趾敲打(其​​餘部分仍然被禁錮)。

  33. 假定所有\p{Math}代碼點都是可見字符的代碼是錯誤的。

  34. 假定\w僅包含字母,數字和下劃線的代碼是錯誤的。

  35. 假設^~是標點符號的代碼是錯誤的。

  36. 假定有變音符號的代碼是錯誤的。

  37. 相信諸如包含任何字母的代碼是錯誤的。

  38. 相信\p{InLatin}的代碼與\p{Latin}被嚴重破壞的代碼相同。

  39. 認為\p{InLatin}幾乎有用的代碼幾乎肯定是錯誤的。

  40. 認為給定$FIRST_LETTER作為某個字母表中的第一個字母而$LAST_LETTER作為同一字母表中的最後一個字母, [${FIRST_LETTER}-${LAST_LETTER}]具有任何含義的代碼幾乎總是完整的錯誤和錯誤,無意義的。

  41. 相信某人的名字只能包含某些字符的代碼是愚蠢的,冒犯性的和錯誤的。

  42. 試圖將Unicode簡化為ASCII的代碼不僅僅是錯誤的,它的犯罪者永遠不能再被允許再次編程。 期。 我甚至沒有積極的態度,他們甚至應該被允許再次看到,因為到目前為止它顯然還沒有做得太好。

  43. 相信有一些假裝文本文件編碼不存在的方法的代碼已經破解並且很危險。 也可能把另一隻眼睛戳出來。

  44. 將未知字符轉換為的代碼? 是破碎的,愚蠢的,braindead,並運行違反標準的建議,其中說不要這樣做 RTFM為什麼不。

  45. 相信它可以可靠地猜測未標記文本文件編碼的代碼是一個瘋狂的混亂和天真的混亂,只有來自宙斯的閃電才能修復。

  46. 相信您可以使用printf寬度來填充和驗證Unicode數據的代碼被破壞並且錯誤。

  47. 相信一旦你用給定的名字成功創建了一個文件的代碼,當你在它的封裝目錄上運行lsreaddir時,你會發現那個文件名是你創建它的名字是錯誤的,壞的和錯誤的。 不要為此感到驚訝!

  48. 相信UTF-16是固定寬度編碼的代碼是愚蠢的,破碎的和錯誤的。 撤銷他們的編程許可。

  49. 將來自一個平面的代碼點視為與來自任何其他平面的代碼點不同的代碼是事實上的錯誤和錯誤。 回到學校。

  50. 相信像/s/i這樣的東西只能匹配"S""s"被破解並且錯誤。 你會感到驚訝。

  51. 使用\PM\pM*來查找字形集群而不是使用\X被破壞並且錯誤。

  52. 應該全心全意鼓勵那些想要回到ASCII世界的人們這樣做,為了榮譽升級,他們應該免費提供預先電動手動打字機來滿足他們的所有數據輸入需求。 發送給他們的信息應該通過一個每行40個字符的電報發送,並由一名快遞員手動發送。 停。

🎁🐪𝕭𝖔𝖎𝖑𝖊𝖗⸗𝖕𝖑𝖆𝖙𝖊𝖋𝖔𝖗𝖀𝖓𝖎𝖈𝖔𝖉𝖊⸗𝕬𝖜𝖆𝖗𝖊𝕮𝖔𝖉𝖊🐪🎁

我自己的樣板往往看起來像這樣:

use 5.014;

use utf8;
use strict;
use autodie;
use warnings; 
use warnings    qw< FATAL  utf8     >;
use open        qw< :std  :utf8     >;
use charnames   qw< :full >;
use feature     qw< unicode_strings >;

use File::Basename      qw< basename >;
use Carp                qw< carp croak confess cluck >;
use Encode              qw< encode decode >;
use Unicode::Normalize  qw< NFD NFC >;

END { close STDOUT }

if (grep /\P{ASCII}/ => @ARGV) { 
   @ARGV = map { decode("UTF-8", $_) } @ARGV;
}

$0 = basename($0);  # shorter messages
$| = 1;

binmode(DATA, ":utf8");

# give a full stack dump on any untrapped exceptions
local $SIG{__DIE__} = sub {
    confess "Uncaught exception: @_" unless $^S;
};

# now promote run-time warnings into stackdumped exceptions
#   *unless* we're in an try block, in which 
#   case just generate a clucking stackdump instead
local $SIG{__WARN__} = sub {
    if ($^S) { cluck   "Trapped warning: @_" } 
    else     { confess "Deadly warning: @_"  }
};

while (<>)  {
    chomp;
    $_ = NFD($_);
    ...
} continue {
    say NFC($_);
}

__END__

😱𝕾𝖀𝕸𝕸𝕬𝕽𝖄😱

我不知道你能得到多少“默認的Unicode”。 那麼,是的,我這樣做:你應該使用Unicode::CollateUnicode::LineBreak 。 也許更多。

正如你所看到的,有太多的Unicode事物,你真的不必擔心在那裡存在諸如“默認為Unicode”之類的東西。

正如我們在5.8版中所做的那樣,你將會發現,將所有這些事情強加於從一開始就沒有被設計的代碼上來解釋它們是不可能的。 你的善意自私剛剛打破了整個世界。

即使你這樣做了,仍然有一些關鍵問題需要大量的思考才能得到解決。 沒有開關可以翻轉。 只有大腦,我的意思是真正的大腦 ,在這裡就足夠了。 有很多你需要學習的東西。 模仿撤退到手動打字機,你根本無法指望在無知中潛行。 這是21世紀的事情,你不能通過故意的無知來希望Unicode。

你必須學習它。 期。 “一切都有效”永遠不會那麼容易,因為這可以保證很多事情不起作用 - 這使得假設有一種方法可以“使其全部工作”。

對於少數幾個非常有限的操作,您可能會得到一些合理的默認值,但不是沒有考慮比我想像的要多得多的東西。

舉一個例子,規範排序會導致一些真正的麻煩。 😭 "\x{F5}" ,,,,, "o\x{303}" o😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭😭 "o\x{304}\x{303}" 'ō'都應該匹配'õ' ,但是你會怎樣做呢? 這比看起來更難,但這是你需要考慮的。 💣

如果我知道關於Perl的一件事,那就是它的Unicode位做和不做的事,我向你保證: “ᴛʜᴇʀᴇɪsɴᴏUɴɪᴄᴏᴅᴇᴍᴀɢɪᴄʙᴜʟʟᴇᴛ” 😞

你不能只是改變一些默認設置,並獲得順利的航行。 確實,我運行🐪並將PERL_UNICODE設置為"SA" ,但僅此而已,甚至主要是針對命令行的東西。 對於實際工作,我會經歷上面列出的所有步驟,並且我非常仔細地做這件事。

😈ƨƨƨɥəəɥɥɐ'λɐpəɔᴉuɐəʌɐɥ'ʞɔnlpoo⅁😈


在我看來, if (var != 0)更好。





perl unicode utf-8