全目標(biāo)70分之 Java進(jìn)階(六):String類的使用和部分源碼分析

????從概念上講苏揣,Java中字符串就是Unicode字符序列黄鳍。例如,"Hello"由H平匈、e框沟、l、l增炭、o 5個(gè)字符組成街望,Java沒(méi)有內(nèi)置的字符串類型,而是在標(biāo)準(zhǔn)Java類庫(kù)中提供了一個(gè)預(yù)定義類弟跑,很自然的叫做String灾前。每個(gè)雙引號(hào)括起來(lái)的字符串都是String類的一個(gè)實(shí)例。

一孟辑、創(chuàng)建String類

? ? String類型對(duì)象主要有兩種創(chuàng)建方式哎甲,第一種字面量賦值:String h = "hello"蔫敲;最常用的方式,如此方式炭玫,先查詢字符串常量池奈嘿,equlas判斷字符串常量池中有無(wú)為true的對(duì)象引用。沒(méi)有則在堆內(nèi)存中創(chuàng)建一個(gè)"hello"對(duì)象本體吞加,并在字符串常量池中添加裙犹,剛創(chuàng)建的堆內(nèi)存中"hello"對(duì)象引用。于此同時(shí)衔憨,如果再聲明一個(gè)String對(duì)象叶圃,String e = "hello";則不會(huì)再創(chuàng)建一個(gè)String對(duì)象践图,而是和變量h一樣獲得字符串常量區(qū)的該String對(duì)象的引用掺冠。

? ? 第二種,String h = new String("hello")码党;這種方式創(chuàng)建的String對(duì)象德崭,既有可能創(chuàng)建出兩個(gè)對(duì)象,也可能創(chuàng)建出一個(gè)對(duì)象揖盘。如果此時(shí)字符串常量區(qū)沒(méi)有值為"hello"對(duì)象眉厨,則會(huì)創(chuàng)建一個(gè)引用對(duì)象(1.6是永久復(fù)制一個(gè)String對(duì)象,1.7后改為復(fù)制實(shí)例的引用)兽狭,如果有則只創(chuàng)建一個(gè)在堆內(nèi)存中(String對(duì)象本體)憾股;

? ? String對(duì)象的值是不可變的,重新復(fù)制String變量只是改變其引用椭符,原對(duì)象沒(méi)有改變(1.8之前是char數(shù)組荔燎,1.8以后改為byte數(shù)組)


final修飾,無(wú)法改變其值

二销钝、== 和 equlas()

? ? 先回顧一下有咨,==和equls()的區(qū)別,==是比較二者值是否相等蒸健,用于基本類型是直接比較二者的值是否相等座享,用于對(duì)象則是比較二者的引用內(nèi)存地址是否相等。

? ? 那么在很多時(shí)候似忧,我們需要對(duì)String類型對(duì)象進(jìn)行比較渣叛,尤其是面試時(shí)經(jīng)常容易問(wèn)到相關(guān)字符串==比較的問(wèn)題,所以我們必須搞懂它盯捌。

? ? 面試中炒狙茫考的例子是:


輸出結(jié)果是false,因?yàn)槭莾蓚€(gè)不同的對(duì)象

? ? a變量賦值對(duì)象創(chuàng)建時(shí),因?yàn)闆](méi)有在字符串常量區(qū)里找到equals為true的String箫攀。所以在堆中創(chuàng)建一個(gè)"abc"對(duì)象肠牲,并且在非堆字符串常量池中創(chuàng)建對(duì)在堆中剛創(chuàng)建abc對(duì)象的引用,注意是引用靴跛,不是對(duì)象實(shí)體缀雳,然后把此引用賦給a變量。

? ? b變量賦值對(duì)象創(chuàng)建時(shí)梢睛,因?yàn)槭莕ew了一個(gè)String對(duì)象肥印,雖然值還是"abc",但是卻是在堆中新創(chuàng)建了一個(gè)對(duì)象绝葡,與上邊的不一樣深碱,有不同的內(nèi)存地址。


字面量賦值方式

? ? a變量賦值對(duì)象創(chuàng)建后挤牛,堆中會(huì)創(chuàng)建一個(gè)"abc"對(duì)象莹痢,然后在非堆字符串常量池中創(chuàng)建其引用种蘸,然后b和c因?yàn)閑qulas到了相同對(duì)象墓赴,所以不創(chuàng)建新的對(duì)象,直接從字符串常量池中獲得"abc"的引用航瞭,因此==判斷時(shí)诫硕,此三個(gè)變量的值都相等,因?yàn)橹赶虻氖峭粋€(gè)對(duì)象刊侯。

? ? 還沒(méi)清楚的話章办,建議看這兩篇文章:

? ??java用這樣的方式生成字符串:String str = "Hello",到底有沒(méi)有在堆中創(chuàng)建對(duì)象滨彻? - 胖君的回答 - 知乎

????請(qǐng)別再拿“String s = new String("xyz");創(chuàng)建了多少個(gè)String實(shí)例”來(lái)面試了吧

? ? String的equals方法藕届,會(huì)比對(duì)兩個(gè)對(duì)象是否是一個(gè)對(duì)象,如果不是那么就逐一的檢查其byte數(shù)組其每一個(gè)數(shù)值是否相等亭饵,都相等返回true休偶。


第一個(gè)if先判斷==,判斷二者引用是否相同辜羊,如果不是踏兜,然后根據(jù)編碼格式比較值
對(duì)比二者的byte數(shù)組,按順序檢查是否每一個(gè)元素的值都相等八秃。

? ? ? ? String類型的空串表示為""碱妆,長(zhǎng)度為0;空串為null昔驱,因?yàn)镾tring對(duì)象的變量也是引用類型疹尾,所以可以為其賦null值。因此判斷String類型有沒(méi)有值時(shí),需要檢查 是否為null和是否長(zhǎng)度為0纳本。

三睡雇、String的intern()方法

? ? intern方法,從1.7開(kāi)始饮醇,如果常量池中已經(jīng)有了這個(gè)字符串它抱,那么直接返回常量池中的它的引用,如果沒(méi)有就將該字符串的對(duì)象的引用保存到常量池中并返回朴艰。

? ? 知道了intern的功能了观蓄,那么它有什么用處?


前兩行并沒(méi)有創(chuàng)建"hello"對(duì)象祠墅,第三行調(diào)用intern方法向常量池中添加了一個(gè)引用

????在上邊的例子中侮穿,第一行第二行并沒(méi)有創(chuàng)建"hello"字符串的實(shí)例,而第三行在常量池中創(chuàng)建了"hello"的引用毁嗦,因此c亲茅、d拿到了同一個(gè)對(duì)象的引用,所以相等狗准。


可見(jiàn)第一行代碼運(yùn)行后克锣,常量池中并沒(méi)有"hello"的引用,第二行時(shí)才添加腔长,所以c和d==e

四袭祟、String類的常用API

? ? 只列舉幾個(gè)常用的方法,全部的可以查看官方文檔或String類源碼捞附。

? ? 1巾乳、int length()? 獲取字符串的長(zhǎng)度,基本上是最常用的方法

? ? 2鸟召、String trim() 獲取去除空格后的字符串

? ? 3胆绊、String[] split(String regex,int limit)?根據(jù)regex字符串對(duì)象值匹配分割字符串生成數(shù)組欧募,limit代表分割后數(shù)組最大長(zhǎng)度


也可以理解把字符串最大分割為limit-1個(gè)字符串

? ? 4压状、String[] split(String regex) 根據(jù)regex字符串對(duì)象值匹配分割字符串生成數(shù)組

? ? 5、String[] substring(int beginIndex) 從beginIndex索引位置開(kāi)始截取槽片,去掉beginIndex之前的部分何缓。

? ? 6津肛、String[] substring(int beginIndex跳昼,int endIndex) 從beginIndex索引位置開(kāi)始截取到endIndex(不包括endIndex),去掉beginIndex之前的部分和endIndex與endIndex之后的部分背传。

兩個(gè)substring方法的區(qū)別

? ? ? ?7剩盒、boolean equals(Object anObject) 傳入對(duì)象與當(dāng)前String對(duì)象為一個(gè)對(duì)象谷婆,或者值相等時(shí)返回true,反之false

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市纪挎,隨后出現(xiàn)的幾起案子期贫,更是在濱河造成了極大的恐慌,老刑警劉巖异袄,帶你破解...
    沈念sama閱讀 212,816評(píng)論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件通砍,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡烤蜕,警方通過(guò)查閱死者的電腦和手機(jī)封孙,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,729評(píng)論 3 385
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)讽营,“玉大人虎忌,你說(shuō)我怎么就攤上這事〕髋簦” “怎么了膜蠢?”我有些...
    開(kāi)封第一講書(shū)人閱讀 158,300評(píng)論 0 348
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)莉兰。 經(jīng)常有香客問(wèn)我挑围,道長(zhǎng),這世上最難降的妖魔是什么贮勃? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 56,780評(píng)論 1 285
  • 正文 為了忘掉前任贪惹,我火速辦了婚禮苏章,結(jié)果婚禮上寂嘉,老公的妹妹穿的比我還像新娘。我一直安慰自己枫绅,他們只是感情好泉孩,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,890評(píng)論 6 385
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著并淋,像睡著了一般寓搬。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上县耽,一...
    開(kāi)封第一講書(shū)人閱讀 50,084評(píng)論 1 291
  • 那天句喷,我揣著相機(jī)與錄音,去河邊找鬼兔毙。 笑死,一個(gè)胖子當(dāng)著我的面吹牛澎剥,可吹牛的內(nèi)容都是我干的锡溯。 我是一名探鬼主播,決...
    沈念sama閱讀 39,151評(píng)論 3 410
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼祭饭!你這毒婦竟也來(lái)了芜茵?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 37,912評(píng)論 0 268
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤倡蝙,失蹤者是張志新(化名)和其女友劉穎九串,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體寺鸥,經(jīng)...
    沈念sama閱讀 44,355評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡蒸辆,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,666評(píng)論 2 327
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了析既。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片躬贡。...
    茶點(diǎn)故事閱讀 38,809評(píng)論 1 341
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖眼坏,靈堂內(nèi)的尸體忽然破棺而出拂玻,到底是詐尸還是另有隱情,我是刑警寧澤宰译,帶...
    沈念sama閱讀 34,504評(píng)論 4 334
  • 正文 年R本政府宣布檐蚜,位于F島的核電站,受9級(jí)特大地震影響沿侈,放射性物質(zhì)發(fā)生泄漏闯第。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 40,150評(píng)論 3 317
  • 文/蒙蒙 一缀拭、第九天 我趴在偏房一處隱蔽的房頂上張望咳短。 院中可真熱鬧,春花似錦蛛淋、人聲如沸咙好。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 30,882評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)勾效。三九已至,卻和暖如春叛甫,著一層夾襖步出監(jiān)牢的瞬間层宫,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 32,121評(píng)論 1 267
  • 我被黑心中介騙來(lái)泰國(guó)打工其监, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留萌腿,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 46,628評(píng)論 2 362
  • 正文 我出身青樓棠赛,卻偏偏與公主長(zhǎng)得像哮奇,于是被迫代替她去往敵國(guó)和親膛腐。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,724評(píng)論 2 351