第四章 面向對象(下)

           

          第四講

          面向對象(下)

          類的繼承

               通過繼承可以簡化類的定義

               Java只支持單繼承,不允許多重繼承。

               可以有多層繼承,即一個類可以繼承某一個類的子類,如類B繼承了類A,類C又可以繼承類B,那么類C也間接繼承了類A

               子類繼承父類所有的成員變量和成員方法,但不繼承父類的構造方法。在子類的構造方法中可使用語句super(參數列表)調用父類的構造方法。

               如果子類的構造方法中沒有顯式地調用父類的構造方法,也沒有使用this關鍵字調用重載的其它構造方法,則在產生子類的實例對象時,系統默認調用父類無參數的構造方法。

            

          class Person

          {

                 private String name="unknown";

                 private int age=0;

                 public Person()

                 {

                 }

                 public Person(String name,int age)

                 {

                        this.name=name;

                        this.age=age;

                 }

                 void getInfo()

                 {

                        System.out.println("姓名:"+name+"\n"+"年齡:"+age);

                 }

          }

           

          class Student extends Person

          {

                 String school="unknown";

                 public Student()

                 {

                        //super();

                        super("張三",18);

                 }

          }

           

          class TestStudent

          {

                 public static void main(String[]args)

                 {

                        Student st=new Student();

                        st.school="小學";

                        System.out.println("學校:"+st.school);

                        st.getInfo();

                        st.school="中學";

                        System.out.println("學校:"+st.school);

                        new Person("李四",20).getInfo();

                 }

          }

          運行結果:

          學校:小學

          姓名:張三

          年齡:18

          學校:中學

          姓名:李四

          年齡:20

          子類對象的實例化過程

               分配成員變量的存儲空間并進行默認的初始化,就是用new關鍵字產生對象后,對類中的成員變量按第三章的表3.1中的對應關系對對象中的成員變量進行初始化賦值。

               綁定構造方法參數,就是new Person(實際參數列表)中所傳遞進的參數賦值給構造方法中的形式參數變量。

               如有this()調用,則調用相應的重載構造方法(被調用的重載構造方法雙從步驟2開始執行這些流程),被調用的重載構造方法的執行流程結束后,回到當前構造方法,當前構造方法直跳轉到步驟6執行。

               顯式或隱式追溯調用父類的構造方法(一直到Object類為止,Object是所有Java類的最頂層父類,在本章后面部分有詳細講解),父類的構造方法雙從步驟2開始對父類執行這些流程,父類的構造方法的執行流程結束后,回到當前構造方法,當前構造方法繼續往下執行。

               進行實例變量的顯式初始化操作,也就是執行在定義成員變量時就對其進行賦值的語句。、

               執行當前構造方法的方法體中的程序代碼

          class Person

          {

                 public String name="unknown";

                 public int age=0;

                 public Person()

                 {

                 }

                 public Person(String name,int age)

                 {

                        this.name=name;

                        this.age=age;

                 }

                 void getInfo()

                 {

                        System.out.println("姓名:"+name+"\n"+"年齡:"+age);

                 }

          }

           

          class Student extends Person

          {

                 String school="unknown";

                 public Student()

                 {

                        //super();

                        super("張三",18);

                 }

                 public Student(String name,int age)

                 {

                        super(name,age);

                 }

                 public Student(String name,int age,String school)

                 {

                        //super(name,age);

                        this(name,age);

                        this.school=school;

                 }

                 public void getInfo()

                 {

                        System.out.println("姓名:"+name+" 年齡:"+age+" 學校:"+school);

                 }

          }

           

          class TestStudent

          {

                 public static void main(String[]args)

                 {

                        new Student().getInfo();

                        Student st=new Student("李四",16);

                        st.getInfo();

                        new Student("王二麻子",21,"清華").getInfo();

                 }

          }

          運行結果:

          姓名:張三 年齡:18 學校:unknown

          姓名:李四 年齡:16 學校:unknown

          姓名:王二麻子 年齡:21 學校:清華

           

          注意看下面代碼的粗體部分及運行結果:

          class Person

          {

                 public String name="unknown";

                 public int age=0;

                 public Person()

                 {

                 }

                 public Person(String name,int age)

                 {

                        this.name=name;

                        this.age=age;

                 }

                 void getInfo()

                 {

                        System.out.println("姓名:"+name+"\n"+"年齡:"+age);

                 }

          }

           

          class Student extends Person

          {

                 String school="unknown";

                 public Student()

                 {

                        //super();

                        super("張三",18);

                 }

                 /*public Student(String name,int age)

                 {

                        super(name,age);

                 }*/

                 public Student(String name,int age,String school)

                 {

                        super(name,age);

                        //this(name,age);

                        this.school=school;

                 }

                 public void getInfo()

                 {

                        System.out.println("姓名:"+name+" 年齡:"+age+" 學校:"+school);

                 }

          }

           

          class TestStudent

          {

                 public static void main(String[]args)

                 {

                        new Student().getInfo();

                        Student st=new Student("李四",16);

                        st.getInfo();

                        new Student("王二麻子",21,"清華").getInfo();

                 }

          }

           

          姓名:張三 年齡:18 學校:unknown

          姓名:unknown 年齡:學校:unknown

          姓名:王二麻子 年齡:21 學校:清華

                                                             

          注意:super()this()調用語句不能同時在一個構造函數中出現。super()this()調用語句只能作為構造函數中的第一句出現。

           

          覆蓋父類的方法

               覆蓋方法必須和被覆蓋的方法具有相同的方法名稱,參數列表和返回值類型。

               如果在子類中想調用父類中的那個被覆蓋的方法,我們可以用super.方法的格式。

               覆蓋方法時,不能使用比父類中被覆蓋的方法更嚴格的訪問權限。

          class Person

          {                                                                                                                                                       

                        public String name="unknown";                                                                         

                        public int age=-1;         

                        public Person()

                        {

                        }

                        public Person(String name,int age)

                        {

                               this.name=name;

                               this.age=age;

                        }                                                                                                      

                        public void getInfo()                                                                                  

                        {

                               System.out.println("name="+name+",age="+age);

                        }                                                                                                                                                                                                                                                                                            

          }                                                            

           

          class Student extend Person

          {

                        public String school="unknown";

                        public Student()

                        {

                               //super();

                               super("wangwu",18);

                        }

                        public Student(String name,int age)

                        {

                               super(name,age);

                        }

                        public Student(String name,int age,String school)

                        {

                               //super(name,age);

                               this(name,age);

                               this.school=school;

                        }

                        public void getInfo()

                        {

                               System.out.print(/*"name="+name+",age="+age+*/"school="+school);

                               super.getInfo();//調用父類的成員方法

                        }

                        public void study()

                        {

                              

                        }

          }                  

           

          class TestStudent

          {

                        public static void main(String[]args)

                        {

                               Student st=new Student("zhangsan",18,"大學");

                               /*st.name="zhangsan";

                               st.age=20;*/

                               st.getInfo();

                              

                       

                        }

          }

          Final關鍵字

               Java中聲明類、屬性和方法時,可使用關鍵字final來修飾。

               final標記的類不能被繼承。

               final標記的方法不能被子類重寫。

               final標記的變量(成員變量或局部變量)即成為常量,只能賦值一次。

               方法中定義的內置類只能訪問該方法內的final類型的局部變量,用final定義的局部變量相當于是一個常量,它的生命周期超出方法運行的生命周期,將一個形參定義成final也是可以的,這就限定了我們在方法中修改形式參數的值。

               public static final共同標記常量時,這個常量就成了全局的常量。

          抽象類

                  java中可以定義一些不含方法體的方法,它的方法體的實現交給該類的子類根據自己的情況實現,這樣的方法就是抽象方法,包含抽象方法的類就叫抽象類。

               抽象類必須用abstract關鍵字來修飾;抽象方法也必須用abstract來修飾。

               抽象類不能被實例化,也就是不能用new關鍵字去產生對象。

               抽象方法只需聲明,而不需實現。

               含有抽象方法的類必須被聲明為抽象類,抽象類的子類必須覆蓋所有的抽象方法后才能被實例化,否則這個子類還是個抽象類。

          接口(interface)

                 如果一個抽象類中的所有方法都是抽象的,我們就可以將這個類用另外一種方式來定義,就是接口的定義。接口是抽象方法和常量值的定義的集合,從本質上講,接口是一種特殊的抽象類,這種抽象類中只包含常量和方法的定義,而沒有變量和方法的實現。

               接口中的成員都是public訪問類型的,接口里的變量默認是用public static final標識的。

               我們可以定義一個新的接口用extends關鍵字去繼承一個已有的接口

               我們也可以定義一個類用implements關鍵字去實現一個接口中的所有方法,我們還可以定義一個抽象類用implements關鍵字去實現一個接口中定義的部分方法。

               一個類可以繼承一個父類的同時,實現一個或多個接口,extends關鍵字必須位于implements關鍵字的之前。

           

          interface Runner

          {

                 /*public static final*/ int ID=05;

                 void run();

          }

           

          interface Animal extends Runner

          {

                 public void breathe();//必須為public類型,以下如同

          }

           

          abstract class LandAnimal implements Animal

          {

                 public void breathe()

                 {

                        System.out.println("LandAnimal ......");

                 }

          }

           

          class Fish implements Animal

          {

                        public void run()

                        {

                               System.out.println("The fish jogs the way is the swimming");

                        }

                        public void breathe()

                        {

                               System.out.println("The fish breath way is the bubbling");

                        }

          }

           

          class TestAnimal

          {

                 public static void main(String[]args)

                 {

                        Fish f=new Fish();

                        f.run();

                        f.breathe();

                        int j=0;

                        //f.ID=2;無法為最終變量 ID 指定值

                        System.out.println(f.ID);

                        System.out.println(Fish.ID);

                        //LandAnimal la=new LandAnimal(); LandAnimal 是抽象的;無法對其進行實例化

                 }

          }

           
          對象的類型轉換

               子類對象可以自動轉換成父類

               父類轉換成子類必須使用強制轉換

               instanceof操作符可以用來判斷一個實例對象是否屬于一個類。

          class A

          {

                        public void func1()

                        {

                               System.out.println("A fun1 is calling");

                        }

                        public void func2()

                        {

                               func1();

                        }

          }

           

          class B extends A

          {

                        public void func1()

                        {    

                                      System.out.println("B func1 is calling");

                        }

                        public void func3()

                        {

                                      System.out.println("B func3 is calling");

                        }

                       

          }

           

          class C

          {

                        public static void main(String[]args)

                        {

                                      B b=new B();

                                      callA(b);

                                      A a=b;

                                      callA(new A());

                        }

                        public static void callA(A a)

                        {

                                      if(a instanceof B)//如果aB類的一個實例對象

                                                    {

                                                                  B b=(B)a;

                                                                  b.func1();

                                                                  b.func2();

                                                                  b.func3();

                                                    }

                                      else

                                                    {

                                                                  a.func1();

                                                                  a.func2();

                                                    }

                        }

          }

               Object類及equals方法

          class Student

          {

                        String name;

                        int age;

                        public Student(String name,int age)

                                      {

                                                    this.name=name;

                                                    this.age=age;

                                      }

                        public boolean equals(Object obj)

                                      {

                                                    Student st=null;

                                                    if(obj instanceof Student)

                                                    {

                                                                  st=(Student)obj;

                                                                  if(st.name==name && st.age==age)

                                                                                return true;

                                                                  else

                                                                                return false;

                                                    }

                                                    else

                                                                  return false;

                                      }

                        public static void main(String[]args)

                                      {

                                                    Student stud1=new Student("zhangsan",20);

                                                    Student stud2=new Student("zhangsan",18);

                                                    if(stud1.equals(stud2))

                                                                  System.out.println("equals");

                                                    else

                                                                  System.out.println("not equals");

                                      }

          }

          接口實例:

          interface PCI

          {

                        void start();

                        void stop();

          }

          class SoundCard implements PCI

          {

                        public void start()

                        {    

                                      System.out.println("hollo");

                        }

                        public void stop()

                        {

                                      System.out.println("ByeBye");

                        }

          }

           

          class NetWork implements PCI

          {

                        public void start()

                        {    

                                      System.out.println("send...");

                        }

                        public void stop()

                        {

                                      System.out.println("stop...");

                        }

          }

           

          class MainBoard

          {

                        public void usePCICard(PCI p)

                        {

                                      p.start();

                                      p.stop();

                        }

          }

           

          class Assembler

          {

                        public static void main(String[]args)

                        {

                                      MainBoard mb=new MainBoard();

                                      NetWork nw=new NetWork();

                                      SoundCard sc=new SoundCard();

                                      mb.usePCICard(nw);

                                      mb.usePCICard(sc);

                        }

                       

          }

          匿名內置類

          interface PCI

          {

                        void start();

                        void stop();

          }

           

          class SoundCard implements PCI

          {

                        public void start()

                        {    

                                      System.out.println("hollo");

                        }

                        public void stop()

                        {

                                      System.out.println("ByeBye");

                        }

          }

           

          class NetWork implements PCI

          {

                        public void start()

                        {    

                                      System.out.println("send...");

                        }

                        public void stop()

                        {

                                      System.out.println("stop...");

                        }

          }

           

          class MainBoard

          {

                        public void usePCICard(PCI p)

                        {

                                      p.start();

                                      p.stop();

                        }

          }

           

           

          class Assembler

          {

                        public static void main(String[]args)

                        {

                                      MainBoard mb=new MainBoard();

                                      NetWork nw=new NetWork();

                                      SoundCard sc=new SoundCard();

                                      mb.usePCICard(nw);

                                      mb.usePCICard(sc);

                                       mb.usePCICard(new PCI()

                                       {

                                                    public void start()

                                                    {     

                                                                  System.out.println("test start");

                                                    }

                                                    public void stop()

                                                    {

                                                                  System.out.println("test stop");

                                                    }

                                       });

                        }

          }

          異常

               異常定義了程序中遇到的非致命的錯誤,而不是編譯時的語法錯誤,如程序要打開一個不存在的文件、網絡連接中斷、操作數越界、裝載一個不存在的類等。

               try,catch語句

               throws關鍵字

               自定義異常與throw關鍵字

               如何對多個異常作出處理

               我們可以在一個方法中使用throw,try…catch語句業實現程序的跳轉

               一個方法被覆蓋時,覆蓋它的方法必須扔出相同的異常或異常的子類。

               如果父類扔出多個異常,那么重寫(覆蓋)方法必須扔出那些異常的一個子集,也就是說不能扔出新的異常

          class Test

          {

                        public int devide(int x,int y) throws DevideByMinusException,ArithmeticException

                        {

                                      if(y<0)

                                                    throw new DevideByMinusException("devide is "+y);

                                      return x/y;

                        }

                        //以下是實現程序的跳轉功能。

                        /*void fun()

                        {

                                      try

                                      {

                                                    if(x==0)

                                                                  throw new XxxException("xxx");

                                                    else

                                                                  throw new YxxException("yyy");

                                                    ......

                                      }

                                      catch(XxxException e)

                                      {

                                      }

                                      catch(YyyException e)

                                      {

                                                    ......

                                      }

                        }*/

          }

           

          class DevideByMinusException extends Exception

          {

                        public DevideByMinusException(String msg)

                        {

                                      super(msg);

                        }

          }

          class TestException

          {

                        public static void main(String[]args)

                        {

                                      Test tt=new Test();

                                      try

                                      {

                                                    tt.devide(4,0);

                                      }

                                      catch(ArithmeticException e)

                                      {

                                     

                                                    System.out.println("Program is running into Arithmetic");

                                                    e.printStackTrace();

                                      }

                                      catch(DevideByMinusException e)

                                      {

                                                    System.out.println("Program is running into DevideByMinusException");

                                                    e.printStackTrace();

                                      }

                                      catch(Exception e)

                                      {

                                                    System.out.println(e.getMessage());

                                      }

                                      finally

                                      {

                                                    System.out.println("finally");

                                      }

                                      System.out.println("The program is running here.");

                        }

          }

          訪問控制



          類本身也有訪問控制,即在定義類的
          class關鍵字前加上訪問控制符,但類本身只有兩種訪問控制,即public和默認,父類不能是privateprotected,否則子類無法繼承。Public修飾的類能被所有的類訪問,默認修飾(即class關鍵字前沒有訪問控制符)的類,只能被同一包中的所有類訪問。

          posted on 2007-06-07 23:35 大頭劍客 閱讀(367) 評論(0)  編輯  收藏 所屬分類: 學習筆記

          <2025年7月>
          293012345
          6789101112
          13141516171819
          20212223242526
          272829303112
          3456789

          導航

          統計

          公告

          寫字樓里寫字間,寫字間里程序員;
          程序人員寫程序,又拿程序換酒錢;
          酒醒只在網上坐,酒醉還來網下眠;
          酒醉酒醒日復日,網上網下年復年;
          但愿老死電腦間,不愿鞠躬老板前;
          奔馳寶馬貴者趣,公交自行程序員;
          別人笑我忒瘋癲,我笑自己命太賤;
          不見滿街漂亮妹,哪個歸得程序員.
          不管前面是地雷陣還是萬丈深淵,
          我都將勇往直前,義無反顧,
          鞠躬盡瘁,死而后已。
          —— 朱镕基總理

          常用鏈接

          留言簿(1)

          隨筆檔案

          文章分類

          文章檔案

          學習園地

          最新隨筆

          搜索

          積分與排名

          最新評論

          主站蜘蛛池模板: 特克斯县| 内江市| 新乡市| 焦作市| 曲阳县| 习水县| 双鸭山市| 石首市| 新疆| 西峡县| 巫溪县| 宁陕县| 贵定县| 陇川县| 安顺市| 从化市| 安龙县| 蒙阴县| 莱西市| 肃宁县| 色达县| 嘉鱼县| 镇宁| 潼关县| 博兴县| 屏东市| 驻马店市| 乌海市| 自贡市| 特克斯县| 长海县| 通海县| 板桥市| 南陵县| 凤山县| 西和县| 新平| 西宁市| 昌平区| 观塘区| 齐齐哈尔市|