JAVA裏面有class關鍵字定義一個類,後面加上自定義的類名便可。如這裏定義的person類,使用class person定義了一個person類,而後在person這個類的類體裏面定義person這個類應該具備的成員變量(即屬性)和方法,如這裏定義的int id和int age這個兩個成員變量,或者叫屬性,這個id表示人的身份證號碼,人應該具備這個屬性,age表示人的年齡,這也是人應該具備的。這樣就在person這個類裏面定義了兩我的應該有的屬性,接下來就是定義方法了,這裏定義了三個方法,分別是getAge()、setAge(int i)和getId(),分別用來獲取人的年齡,設置人的年齡,獲取人的id,getAge()方法獲取了人的年齡後,將獲取到的值返回,因此使用了return age語句,getId()方法也使用了return id語句用於返回獲取到的id的值。函數
在JAVA裏面的任何變量首先應該要聲明,而後再賦值,而後再使用。成員變量和局部變量有一個重要區別:成員變量在類裏面聲明時若是不進行初始化,那麼JAVA會默認給它初始化,而局部變量JAVA不會默認給它初始化,因此在方法裏面聲明一個局部變量若是不給它初始化時就會出錯。默認初始化大多數都是0,boolean類型的爲false,引用類型的爲null,如過不記得JAVA對成員變量默認的初始化是多少的話,那就這樣作,定義一個成員變量,不給它初始化,而後直接打印這個成員變量,打印出來的結果就是JAVA默認的初始化的值。spa
引用類型和基本類型有着巨大的區別,當聲明一個int i=0時,系統會立刻給這個i分配一個內存空間(在棧內存裏面分配一小塊區域用來裝數字0),裏面裝着一個值爲0,之後使用i這個名字立刻就能夠訪問這個內存空間裏面的值,這就是基本數據類型,因此基礎類型就只佔一塊內存。基礎類型以外的類型全都叫引用類型,咱們定義一個Mouse m,這個m就是一個引用類型的數據。引用類型有什麼重要的特徵——引用類型佔2塊內存。咱們定義好這個類以後,須要使用new關鍵字把這個類的對象實例化出來,也就是真真正正造出一個對象出來才能使用這個對象。code
如何在內存中區分類和對象對象
類是靜態的概念,是位於代碼區裏面。對象是new出來的,它是位於堆內存,爲何對象要位於堆內存?由於堆內存是用來動態分配內存的,只有在運行當中才會new一個對象放堆內存裏面,那這個對象到底有多大個,這個東西你不知道,你沒有辦法提早知道,因此你沒有辦法提早分配內存給這個對象,你只有在運行期間才能去分配它。什麼叫運行期間?敲JAVAC這個命令那是在編譯期間,編譯完成後再敲JAVA命令,那就是運行期間了。只有在運行期間,纔可以明白這個對象到底要分配多大的空間給它,因此把它放在堆內存裏面,堆內存比較大,動態分配內存用它。若是這個對象不用了,那它就是垃圾,那麼就等着垃圾收集器把它收集回去,釋放掉佔用的內存。blog
記住,之後一提到引用,腦子裏立刻浮現引用那就是一小塊內存指向一大塊內存。內存
使用new關鍵字來建立一個新的對象。get
在內存中分析類和對象的關係編譯器
假設這裏有一個類C,咱們定義了一個類class C,而後在這個類裏面定義了兩個成員變量: int i和int j。定義好了這兩個成員變量之後,咱們寫了一個main()方法(public static void main(Strng[] args)),程序開始執行。第一句咱們寫了 C c1 = new C(),這句的代碼是咱們至關於在堆內存裏建立了一個對象,同時也建立了這個對象的一個引用對象c1,c1位於棧內存中,c1這個引用對象指向堆中一大塊內存,這一大塊內存裏面裝着new出來的那個對象。這裏面咱們通常來講是new出來兩個對象c1和c2,固然,實際上,嚴格來說,c1和c2叫作對象的引用,有時候,簡稱new出來了兩個對象,c1和c2。你腦子裏立刻要浮現出兩塊內存,c1指向一塊,c2指向一塊。局部變量是分配在棧內存裏面的,main方法裏面的c1和c2都是局部變量,因此在棧裏面分配了兩小塊內存出來,一塊是c1的,一塊是c2的,c1這塊內存裏面裝着一個值,或者叫裝着一個地址,這個地址是什麼,咱們不知道,咱們只知道根據這個值就能找到new出來的C這個類裏面的一個對象,而在這個對象裏面有它本身的成員變量i和j,裏面的兩小塊內存是分別用來裝i和j的值的,由於每個對象都有本身不一樣的成員變量的值,因此c1指向的那塊對內存裏面又分紅一小塊一小塊內存,每個小塊的內存都裝着這個對象的成員變量(或者叫屬性)。如這裏的第一小塊裝着i的值,第二小塊裝着j的值,因此當咱們去訪問第一小塊裏面裝着的成員變量時,咱們應該這樣寫:c1.i,這樣就拿到了i的值,c1.j,這樣就拿到了j的值。同理,c2這個對象也指向了一個new出來的C這個類裏面的另外一個對象,這個對象也有成員變量i和j,只不過和c1指向的那個對象裏的i和j的值不一樣而已。要訪問這個這個對象的成員變量時 ,也是要c2.i,c2.j這樣去訪問。編譯
在面向對象裏面有一個特殊的方法,叫構造方法。class
構造方法是用來建立一個新的對象的,與new組合在一塊兒用,使用new+構造方法建立一個新的對象。你new一個東西的時候,實際上你調用的是一個構造方法,構造方法就是把本身構形成一個新的對象,因此叫構造方法,構造一個新對象用的方法叫構造方法。
構造方法比較特殊,構造方法的名字必須和類的名字徹底如出一轍,包括大小寫,而且沒有返回值。如原來定義的一個person類,在類裏面聲明瞭兩個成員變量id與age,這時候你能夠再爲這個person類定義一個它的構造方法person(int n,int i),這個方法的名字和類名徹底相同,而且沒有返回值,也就是在這個方法前面不能寫任何的方法的返回類型修飾符,連void都不能夠寫。
構造方法範例:
1 public class Person { 2 int id; //在person這類裏面定義兩個成員變量id和age, 3 int age=20; //給成員變量age賦了初值爲20 4 5 /**這裏就是person這個類的一個構造方法 6 * 構造方法的規則很簡單,和類名要徹底同樣,一點都不能錯,包括大小寫。 7 * 而且沒有返回值,不能寫void在它前面修飾 8 * @param _id 9 * @param _age 10 */ 11 public Person(int _id,int _age ) { 12 id = _id; 13 age = _age; 14 } 15 }
構造方法寫好後就和new組合在一塊兒使用,new的做用是構建一個新對象,創造一個新對象,因此new的時候實際當中調用的是構造方法。只有調用了這個構造方法才能構造出一個新的對象。例如:
1 public static void main(String[] args) { 2 Person tom = new Person(1, 25); // 調用person這個構造方法建立一個新的對象,並給這個對象的成員變量賦初始值 3 }
下面是在main方法裏面調用person構造方法時的內存分析狀況:
當方法調用完成以後,棧裏面爲它分配的空間所有都要消失,即把這個方法調用時分配給它的內存空間釋放出來,因此這個構造方法person調用完成以後,棧內存裏面分配的兩小塊內存_id和_age自動消失了。這樣就把它們所佔的空間讓了出來,讓其餘的方法去佔用。而new出來的對象則永遠留在了堆內存裏面。
聲明一個類,若沒有在類中指定其構造方法(構造函數)時,編譯器會爲這個類自動添加形如類名( ){ }的構造函數。
如:
1 class point{//這裏聲明一個類時並無給它指定其構造方法。 2 int x; 3 int y; 4 }
但在main方法裏面咱們卻能夠這樣使用:
1 public static void main(String[] args){ 2 point p = new point(); 3 }
這裏這樣寫是能夠的,當沒有給這個類指明構造方法時,系統會默認地給這個類加上point ( ) { }這樣一個空的構造方法。因此才能夠在main方法中使用
point p = new point(); 實際上你調用的就是編譯器默認給它加上的point ( ) { }這個構造方法,在這個構造方法當中,默認地把類裏面的成員變量x和y初始值設爲0。正是由於系統給它默認加上這麼一個構造方法,因此才能在main方法裏面調用。但要記住一點,一旦給這個類裏面指定了構造方法,那麼系統就不會再給這個類添加構造方法了。