public class MathTest{ public static void main(String[]args){ double a = 0.01, b = 0.09; System.out.PRint(a+b); }}打印的結(jié)果為什么是 0.09999999999999999 而非 0.1,發(fā)生精度損失, 無論是 double還是 float 都會(huì)遇到這個(gè)問題,就拿 float 說話, float 的 0.1 二進(jìn)制形式是 00111101110011001100110011001101,根據(jù)符號位換算為 10 進(jìn)制表達(dá)的值精確應(yīng)該是這樣計(jì)算110011001100110011001101 乘以 2 的負(fù) 27 次方,實(shí)際值是0.100000001490116119384765625 這樣就產(chǎn)生了實(shí)際誤差。
例
public float getLeftMoney() throws Exception {// TODO Auto-generated method stubfloat m = new MoneyDaoImpl().CountAllMoney();float c = new DetailsDaoImpl().countDetailsMoney();flaot less = m-c;System.out.println(m);System.out.println(c);System.out.println(less);return less;}解決辦法:
public float getLeftMoney() throws Exception { // TODO Auto-generated method stub float m = new MoneyDaoImpl().CountAllMoney(); float c = new DetailsDaoImpl().countDetailsMoney(); BigDecimal b1 = new BigDecimal(Float.toString(m)); BigDecimal b2 = new BigDecimal(Float.toString(c)); System.out.println(m); System.out.println(c); Float less = b1.subtract(b2).floatValue(); System.out.println(less); return less;}疑問二:Null 屬于什么類型?解:
①heep (堆)是一個(gè)可動(dòng)態(tài)申請的內(nèi)存空間,一般所有創(chuàng)建的對象都放在這里。stack (棧)是一個(gè)先進(jìn)后出的數(shù)據(jù)結(jié)構(gòu),通常用于保存方法(函數(shù))中的參數(shù),局部變量。stack (棧)的空間小,但速度比較快, 存放對象的引用,通過棧中的地址索引可以找到堆中的對象。②棧( java stacks)也是線程私有的,它的生命周期與線程相同。虛擬機(jī)棧描述的是 java方法執(zhí)行的內(nèi)存模型:每個(gè)方法被執(zhí)行的時(shí)候都會(huì)同時(shí)創(chuàng)建一個(gè)棧用于存儲(chǔ)局部變量表、操作棧、動(dòng)態(tài)鏈接、方法出口等信息。每一個(gè)方法被調(diào)用直至執(zhí)行完成的過程,就對應(yīng)著一個(gè)棧幀在虛擬機(jī)棧中從入棧到出棧的過程。堆( java Heap)是 java 虛擬機(jī)所管理的內(nèi)存中最大的一塊。 Java 堆是被所有線程共享的一塊內(nèi)存區(qū)域,在虛擬機(jī)啟動(dòng)時(shí)創(chuàng)建。此內(nèi)存區(qū)域的唯一目的就是存放對象實(shí)例,幾乎所有的對象實(shí)例都在這里分配內(nèi)存。
疑問四:什么是實(shí)例變量?什么是類變量解:
①類變量也叫靜態(tài)變量,也就是在變量前加了 static 的變量,類變量在創(chuàng)建對象前就已經(jīng)在內(nèi)存中存在,隨類的創(chuàng)建而創(chuàng)建;實(shí)例變量也叫對象變量,即沒加 static 的變量。②類變量是所有對象共有,其中一個(gè)對象將它值改變,其他對象得到的就是改變后的結(jié)果;而實(shí)例變量則屬對象私有,某一個(gè)對象將其值改變,不影響其他對象。③所有的實(shí)例對象都共用一個(gè)類變量,內(nèi)存中只有一處空間是放這個(gè)類變量值的。因此,如果一個(gè)對象把類變量值改了,另外一個(gè)對象再取類變量值就是改過之后的了。在創(chuàng)建實(shí)例對象的時(shí)候,內(nèi)存中會(huì)為每一個(gè)實(shí)例對象的每一個(gè)非靜態(tài)成員變量開辟一段內(nèi)存空間,用來存儲(chǔ)這個(gè)對象所有的非靜態(tài)成員變量值,即使兩個(gè)不同的實(shí)例對象是屬于同一個(gè) class 類,但是它們的同名非靜態(tài)成員變量在內(nèi)存中占用的空間是不同的。
public class A{ static int a = 0; //類變量 private int b = 0; //實(shí)例變量}Public class B{ public void main (String[] args){ A a1 = new A(); A a2 = new A(); a1.a = 3; // 等同于 A.a = 3; a1.b = 4 ; System.out.println(a2.a); //結(jié)果為 3 //類變量是針對所有對象的,所以 a1 改變 a, a2 的 a 也改變 System.out.println(a2.b); //結(jié)果為 0 //實(shí)例只改變自身的,所以 a1 對象的 b 改變,不影響對象 a2 的 b 變量 }}疑問五:重載和重寫的區(qū)別?解:
①重載 Overload 表示同一個(gè)類中可以有多個(gè)名稱相同的方法,但這些方法的參數(shù)列表各不相同(即參數(shù)個(gè)數(shù)或類型不同)。
條件: A)方法名必須相同(大小寫必須一致才算是相同) B)參數(shù)列表不同,參數(shù)列表不同又分為:參數(shù)列表的個(gè)數(shù)不同;參數(shù)列表的排列順序不同;參數(shù)列表的數(shù)據(jù)類型不同。必須同時(shí)滿足條件 A 和 B 才叫方法的重載。
注意:
②重寫 Override 表示子類中的方法可以與父類中的某個(gè)方法的名稱和參數(shù)完全相同,通過子類創(chuàng)建的實(shí)例對象調(diào)用這個(gè)方法時(shí),將調(diào)用子類中的定義方法,這相當(dāng)于把父類中定義的那個(gè)完全相同的方法給覆蓋了,這也是面向?qū)ο缶幊痰亩鄳B(tài)性的一種表現(xiàn)。子類覆蓋父類的方法時(shí),只能比父類拋出更少的異常,或者是拋出父類拋出的異常的子異常,因?yàn)樽宇惪梢越鉀Q父類的一些問題,不能比父類有更多的問題。子類方法的訪問權(quán)限只能比父類的更大,不能更小。如果父類的方法是 private 類型,那么,子類則不存在覆蓋的限制,相當(dāng)于子類中增加了一個(gè)全新的方法。
在覆蓋要注意以下的幾點(diǎn): A) 覆蓋的方法的標(biāo)志必須要和被覆蓋的方法的標(biāo)志完全匹配,才能達(dá)到覆蓋的效果; B) 覆蓋的方法的返回值必須和被覆蓋的方法的返回一致; C)覆蓋的方法所拋出的異常必須和被覆蓋方法的所拋出的異常一致,或者是其子類; D) 被覆蓋的方法不能為 private,否則在其子類中只是新定義了一個(gè)方法,并沒有對其進(jìn)行覆蓋。
新聞熱點(diǎn)
疑難解答
圖片精選