簡體   English   中英

在Java中,使用從InputStream.read()返回的int調用Character.isXxx()方法是否安全?

[英]In Java, is it safe to call Character.isXxx() methods with an int returned from InputStream.read()?

讀取文本文件時,我想執行以下操作:

InputStream input = ...;
int read = input.read();
if (Character.isWhitespace(read)) {
    // do something with the whitespace
}

另一種選擇是檢查負的read()返回值(也就是輸入的結尾)並顯式轉換:

InputStream input = ...;
int read = input.read();
if (read >= 0 && Character.isWhitespace((char) read)) {
    // do something with the whitespace
}

但是,這涉及一個額外的分支和強制轉換,我希望我的代碼盡可能高效,所以我更喜歡第一種方法。

但是,我希望我的代碼更加健壯:),而且我不確定第一種方法是否會產生細微的問題。 根據我的收集,Unicode將0xFFFF0xFFFFFFFF都定義為非字符,因此我認為這是安全的。 但是專家怎么說?

只是為了確保,問題涉及我的方法對所有 Character.isXxx()方法是否安全,而不僅僅是Character.isWhitespace()是安全的。

InputStream.read()方法讀取單個8位字節 ,並將其作為32位int返回,范圍為0x00 - 0xFF ,或者在EOF上返回-1

接受32位int作為輸入的Character.isXXX()方法期望在0x00 - 0x10FFFF范圍內的完整Unicode代碼點 如果文件包含7位ASCII字符(其中字節0x00 - 0x7F映射到代碼點U+0000 - U+007F )或ISO-8859-1(其中字節0x00 - 0xFF ),則單個字節可以按原樣表示完整的代碼點。 0x00 - 0xFF映射到代碼點U+0000 - U+00FF )。 如果文件使用任何其他編碼,則不能保證任何給定的字節都會照原樣映射到相同值的代碼點,尤其是如果該字節大於0x7F (大多數0x7F位編碼使用相同的字節) ASCII兼容的值-並非全部!)。

所述Character.isXXX()接受一個16位的方法char作為輸入期望的范圍內的UTF-16 codeunit 0x00 - 0xFFFF 單個char可以按原樣保存Unicode代碼點,直到代碼點U+FFFF為止。 但是,這些方法支持UTF-16替代,因此無法處理U+FFFF以上的Unicode代碼點(需要2個char值來表示它們)。

因此,要回答您的問題-您read()從文件中read()任何給定字節並將其原樣傳遞給Character.isXXX()方法並獲得可靠的結果嗎? 答案是- 它取決於文件的實際編碼 如果文件以7位ASCII或8位ISO-8859-1編碼,則為是。 否則, 也許 ,但通常僅用於字節0x7F,因為字節0x80 - 0xFF是特定於編碼的,並且將取決於字節和Unicode代碼點之間的特定編碼映射方式(假設文件甚至使用7/8位編碼開始用)。

是的,這很安全。 對於0xFFFFFFFF ,所有isXxx方法都返回false。 實際上,對於0x000FFFFF所有內容都是如此,因為這些值在Unicode中未定義。 對於0xFFFF ,盡管isBmpCodePoint為true,但isBmpCodePoint相同。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM