java不可变类型_Java中的值类型:为什么它们不可变?
java不可變類型
值類型不必是不變的。 但是他們是。
在上一篇文章中,我討論了Java中指針與引用之間的區(qū)別以及如何傳遞方法參數(shù)(按值傳遞或按引用傳遞)。 這些與Java中尚不存在的值類型密切相關(guān)(尚未)。
John Rose,Brian Goetz和Guy Steele 提出了一個建議 ,詳細介紹了值類型將如何/可能在Java中工作,并且還有一些很好的文章。 我已經(jīng)閱讀了我非常喜歡的“值類型:改造Java的類型系統(tǒng)” ,我建議閱讀。 如果建議過于密集,以至于您無法關(guān)注該主題,則可以先閱讀該文章。 它非常概括了背景,值類型是什么,優(yōu)點,為什么Java不實現(xiàn)值類型是一個問題以及為什么它不是瑣碎的問題。 即使術(shù)語“值類型”也可以用來表示不同的東西,我也會在提案和文章中使用它。
我們?nèi)绾蝹鬟f參數(shù)與我們在變量中存儲什么
您可能還記得上一篇文章,我詳細介紹了Java根據(jù)參數(shù)的類型按引用或按值傳遞方法參數(shù):
- 當(dāng)參數(shù)是對象時傳遞引用
- 參數(shù)為原始值時按值排序。
在原始帖子上以及在JCG重新發(fā)布 上都有一些評論,這些評論抱怨我關(guān)于通過引用傳遞論點的術(shù)語。 注釋指出,參數(shù)總是按值傳遞,因為變量已包含對對象的引用。 實際上,變量包含位。 即使了解我們?nèi)绾蜗胂筮@些位以及在交流時使用什么術(shù)語,這一點很重要。 我們可以說
如果我們遵循思想#1,則根據(jù)參數(shù)(對象或基元)的實際性質(zhì),參數(shù)傳遞是按值和/或按引用。 如果我們遵循思想#2,則變量將根據(jù)其類型的性質(zhì)存儲參考和/或值。 我個人想寫的時候
Triangle triangle;則可變triangle是三角形,而不是對三角形的引用。 但這與我的大腦到底有什么關(guān)系并不重要。 在情況#1或#2中,對于類類型和基元都有不同的方法。 如果我們在語言中引入值類型,則區(qū)別將變得更加普遍和易于理解。
值類型是不可變的
我解釋說,基于類型的隱式參數(shù)傳遞不會引起任何問題,因為基元是不可變的,因此,當(dāng)作為方法參數(shù)傳遞時,即使通過引用傳遞它們也無法更改。 所以我們通常不在乎。 值類型沒有不同。 值類型也是不可變的,因為它們是值,并且值不變。 例如,PI的值為3.145926…,并且它永遠不會改變。
但是,這種不變性在編程中意味著什么? 值可以是實數(shù),整數(shù)或復(fù)合值類型,它們在內(nèi)存中均以位表示。 可以更改內(nèi)存中的位(除非內(nèi)存是ROM)。
在對象不變的情況下,相當(dāng)簡單。 宇宙中某個地方有一個我們無法改變的物體。 可能有許多保存對象的變量(對其有一個引用),并且代碼可以依賴于這樣的事實,即表示對象實際值的存儲位置中的位不變(或多或少)。
在值類型的情況下,這有點不同,并且這種差異是由于相同位在表示對象時對表示值類型的位的解釋不同。
值類型沒有身份
值類型沒有身份。 您不能有兩個保存值3 int變量并區(qū)分另一個。 它們具有相同的價值。 當(dāng)類型更復(fù)雜時,也是如此。
假設(shè)我有一個具有兩個字段的值類型,例如
ValueType TwoFields {int count;double size;}說我有兩個變量
Twofields tF1 = new TwoFields(1,3.14)Twofields tF2 = new TwoFields(1,3.14)我不能告訴其他變量tF1和tF2 。 如果他們的對象,他們是equals彼此但不==對方。 對于值類型,沒有==因為它們沒有身份。
如果TwoFields是不可變的類,我不能或不應(yīng)該寫
TwoFields tF;...tF.count++;或一些類似的結(jié)構(gòu)。 但我仍然可以寫
TwoFields tF;...tF = new TwoFields(tF.count+1, tF.size)保持原始對象不變。 如果TwoFields是值類型,則無論哪種構(gòu)造,都將創(chuàng)建一個新值。
值類型作為參數(shù)
值類型如何作為方法參數(shù)傳遞呢? 可能將值復(fù)制到參數(shù)變量。 可能會傳遞一些參考。 但是,這取決于編譯器(是Java還是其他語言)。 為什么?
- 值類型通常很小。 至少它們應(yīng)該很小。 巨大的值類型失去了值類型提供的優(yōu)點,但有缺點。
- 值類型是不可變的,因此像原始類型一樣復(fù)制它們沒有問題。 可以按值傳遞它們的方式與“ Java的所有內(nèi)容都按值傳遞”的方式相同。
- 它們沒有身份,不能引用它們。
但這不僅是將它們作為參數(shù)傳遞。 這也是分配變量的方式。 看代碼
Twofields tF1 = new TwoFields(1,3.14)Twofields tF2 = new TwoFields(1,3.14)比較一下
Twofields tF1 = new TwoFields(1,3.14)Twofields tF2 = tF1如果TwoFields是值類型,則兩個版本之間應(yīng)該沒有區(qū)別。 它們必須產(chǎn)生相同的結(jié)果(盡管在編譯時可能不會通過相同的代碼)。 在這方面,參數(shù)傳遞和變量賦值之間沒有真正的區(qū)別。 即使實際變量作為位包含對存儲值的某些存儲位置的某些引用,也會復(fù)制值。
摘要
在我開始撰寫本文時:值類型不必是不變的。 這不是語言設(shè)計師決定的事情。 他們可以自由地實現(xiàn)可變的東西,但是在那種情況下,它將不是值類型。 值類型是不可變的。
翻譯自: https://www.javacodegeeks.com/2016/01/value-types-java-immutable.html
java不可變類型
總結(jié)
以上是生活随笔為你收集整理的java不可变类型_Java中的值类型:为什么它们不可变?的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: sql 解析 java_将Java 8流
- 下一篇: java-ee-api_刷新器-Java