日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > java >内容正文

java

小师妹学JavaIO之:文件编码和字符集Unicode

發(fā)布時間:2024/2/28 java 36 豆豆
生活随笔 收集整理的這篇文章主要介紹了 小师妹学JavaIO之:文件编码和字符集Unicode 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

文章目錄

  • 簡介
  • 使用Properties讀取文件
  • 亂碼初現(xiàn)
  • 字符集和文件編碼
  • 解決Properties中的亂碼
  • 真.終極解決辦法
  • 總結

簡介

小師妹一時興起,使用了一項從來都沒用過的新技能,沒想?yún)s出現(xiàn)了一個無法解決的問題。把大象裝進冰箱到底有幾步?亂碼的問題又是怎么解決的?快來跟F師兄一起看看吧。

更多精彩內(nèi)容且看:

  • 區(qū)塊鏈從入門到放棄系列教程-涵蓋密碼學,超級賬本,以太坊,Libra,比特幣等持續(xù)更新
  • Spring Boot 2.X系列教程:七天從無到有掌握Spring Boot-持續(xù)更新
  • Spring 5.X系列教程:滿足你對Spring5的一切想象-持續(xù)更新
  • java程序員從小工到專家成神之路(2020版)-持續(xù)更新中,附詳細文章教程

使用Properties讀取文件

這天,小師妹心情很愉悅,吹著口哨唱著歌,標準的45度俯視讓人好不自在。

小師妹呀,什么事情這么高興,說出來讓師兄也沾點喜慶?

小師妹:F師兄,最新我發(fā)現(xiàn)了一種新型的讀取文件的方法,很好用的,就跟map一樣:

public void usePropertiesFile() throws IOException {Properties configProp = new Properties();InputStream in = this.getClass().getClassLoader().getResourceAsStream("www.flydean.com.properties");configProp.load(in);log.info(configProp.getProperty("name"));configProp.setProperty("name", "www.flydean.com");log.info(configProp.getProperty("name"));}

F師兄你看,我使用了Properties來讀取文件,文件里面的內(nèi)容是key=value形式的,在做配置文件使用的時候非常恰當。我是從Spring項目中的properties配置文件中得到的靈感,才發(fā)現(xiàn)原來java還有一個專門讀取屬性文件的類Properties。

小師妹現(xiàn)在都會搶答了,果然青出于藍。

亂碼初現(xiàn)

小師妹你做得非常好,就這樣觸類旁通,很快java就要盡歸你手了,后面的什么scala,go,JS等估計也統(tǒng)統(tǒng)不在話下。再過幾年你就可以升任架構師,公司技術在你的帶領之下一定會蒸蒸日上。

做為師兄,最大的責任就是給小師妹以鼓勵和信心,給她描繪美好的未來,什么出任CEO,贏取高富帥等全都不在話下。聽說有個專業(yè)的詞匯來描述這個過程叫做:畫餅。

小師妹有點心虛:可是F師兄,我還有點小小的問題沒有解決,有點中文的小小亂碼…

我深有體會的點點頭:馬賽克是阻礙人類進步的絆腳石…哦,不是馬賽克,是文件亂碼,要想弄清楚這個問題,還要從那個字符集和文件編碼講起。

字符集和文件編碼

在很久很久以前,師兄我都還沒有出生的時候,西方世界出現(xiàn)了一種叫做計算機的高科技產(chǎn)品。

初代計算機只能做些簡單的算數(shù)運算,還要使用人工打孔的程序才能運行,不過隨著時間的推移,計算機的體積越來越小,計算能力越來越強,打孔已經(jīng)不存在了,編程了人工編寫的計算機語言。

一切都在變化,唯有一件事情沒有變化。這件事件就是計算機和編程語言只流傳在西方。而西方日常交流使用26個字母加有限的標點符號就夠了。

最初的計算機存儲可以是非常昂貴的,我們用一個字節(jié)也就是8bit來存儲所有能夠用到的字符,除了最開始的1bit不用以外,總共有128中選擇,裝26個小寫+26個大寫字母和其他的一些標點符號之類的完全夠用了。

這就是最初的ASCII編碼,也叫做美國信息交換標準代碼(American Standard Code for Information Interchange)。

后面計算機傳到了全球,人們才發(fā)現(xiàn)好像之前的ASCII編碼不夠用了,比如中文中常用的漢字就有4千多個,怎么辦呢?

沒關系,將ASCII編碼本地化,叫做ANSI編碼。1個字節(jié)不夠用就用2個字節(jié)嘛,路是人走出來的,編碼也是為人來服務的。于是產(chǎn)生了各種如GB2312, BIG5, JIS等各自的編碼標準。這些編碼雖然與ASCII編碼但是相互之間缺并不兼容。

這嚴重的影響了國際化的進程,這樣還怎么去實現(xiàn)同一個地球,同一片家園的夢想?

于是國際組織出手了,制定了UNICODE字符集,為所有語言的所有字符都定義了一個唯一的編碼,unicode的字符集是從U+0000到U+10FFFF這么多個編碼。

小師妹:F師兄,那么unicode和我平時聽說的UTF-8,UTF-16,UTF-32有什么關系呢?

我笑著問小師妹:小師妹,把大象裝進冰箱有幾步?

小師妹:F師兄,腦筋急轉彎的故事,已經(jīng)不適合我了,大象裝進冰箱有三步,第一打開冰箱,第二把大象裝進去,第三關上冰箱,完事了。

小師妹呀,作為一個有文化的中國人,要真正的承擔起民族復興,科技進步的大任,你的想法是很錯誤的,不能光想口號,要有實際的可操作性的方案才行,要不然我們什么時候才能夠打造秦芯,唐芯和明芯呢?

師兄說的對,可是這跟unicode有什么關系呢?

unicode字符集最后是要存儲到文件或者內(nèi)存里面的,那怎么存呢?使用固定的1個字節(jié),2個字節(jié)還是用邊長的字節(jié)呢?根據(jù)編碼方式的不同,可以分為UTF-8,UTF-16,UTF-32等多種編碼方式。

其中UTF-8是一種變長的編碼方案,它使用1-6個字節(jié)來存儲。UTF-16使用2個或者4個字節(jié)來存儲,JDK9之后的String的底層編碼方式變成了兩種:LATIN1和UTF16。

而UTF-32是使用4個字節(jié)來存儲。這三種編碼方式中,只有UTF-8是兼容ASCII的,這也是為什么國際上UTF-8編碼方式比較通用的原因(畢竟計算機技術都是西方人搞出來的)。

解決Properties中的亂碼

小師妹,要解決你Properties中的亂碼問題很簡單,Reader基本上都有一個Charsets的參數(shù),通過這個參數(shù)可以傳入要讀取的編碼方式,我們把UTF-8傳進去就行了:

public void usePropertiesWithUTF8() throws IOException{Properties configProp = new Properties();InputStream in = this.getClass().getClassLoader().getResourceAsStream("www.flydean.com.properties");InputStreamReader inputStreamReader= new InputStreamReader(in, StandardCharsets.UTF_8);configProp.load(inputStreamReader);log.info(configProp.getProperty("name"));configProp.setProperty("name", "www.flydean.com");log.info(configProp.getProperty("name"));}

上面的代碼中,我們使用InputStreamReader封裝了InputStream,最終解決了中文亂碼的問題。

真.終極解決辦法

小師妹又有問題了:F師兄,這樣做是因為我們知道文件的編碼方式是UTF-8,如果不知道該怎么辦呢?是選UTF-8,UTF-16還是UTF-32呢?

小師妹問的問題越來越刁鉆了,還好這個問題我也有準備。

接下來介紹我們的終極解決辦法,我們將各種編碼的字符最后都轉換成unicode字符集存到properties文件中,再讀取的時候是不是就沒有編碼的問題了?

轉換需要用到JDK自帶的工具:

native2ascii -encoding utf-8 file/src/main/resources/www.flydean.com.properties.utf8 file/src/main/resources/www.flydean.com.properties.cn

上面的命令將utf-8的編碼轉成了unicode。

轉換前:

site=www.flydean.com name=程序那些事

轉換后:

site=www.flydean.com name=\u7a0b\u5e8f\u90a3\u4e9b\u4e8b

再運行下測試代碼:

public void usePropertiesFileWithTransfer() throws IOException {Properties configProp = new Properties();InputStream in = this.getClass().getClassLoader().getResourceAsStream("www.flydean.com.properties.cn");configProp.load(in);log.info(configProp.getProperty("name"));configProp.setProperty("name", "www.flydean.com");log.info(configProp.getProperty("name"));}

輸出正確的結果。

如果要做國際化支持,也是這樣做的。

總結

千辛萬苦終于解決了小師妹的問題,F師兄要休息一下。

本文的例子https://github.com/ddean2009/learn-java-io-nio

本文作者:flydean程序那些事

本文鏈接:http://www.flydean.com/io-charsets-properties/

本文來源:flydean的博客

歡迎關注我的公眾號:程序那些事,更多精彩等著您!

總結

以上是生活随笔為你收集整理的小师妹学JavaIO之:文件编码和字符集Unicode的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。