java學習中,面向對象的三大特性:封裝、繼承、多態 以及 super關鍵字和方法的重寫(java 學習中的小記錄)
作者:王可利(Star·星星)
封裝
權限修飾符:public 公共的,private 私有的
封裝的步驟:
1.使用private 修飾需要封裝的成員變量。
2.提供一個公開的方法設置或者訪問私有的屬性
設置 通過set方法,命名格式: set屬性名(); 屬性的首字母要大寫
訪問 通過get方法,命名格式: get屬性名(); 屬性的首字母要大寫
1 //姓名設置器方法
2 public void setName(String name){
3 this.name = name;
4 }
5 //姓名訪問器方法
6 public String getName(){
7 return name;
8 }
代碼書寫的規范:java開發中一般類成員變量(屬性),都是封裝起來的 。
問題:是不是所有的屬性都需要使用 set 和 get 方法?
不一定,按照需求來定。
封裝的作用:1. 框架 2. 工具類
封裝的好處:1. 提高了數據的安全性 2. 操作簡單 3. 隱藏了方法的實現。
1 class Student{
2 private String name;//成員變量被修飾之後只能在本類中進行訪問了,私有的了。
3 private String sex;//如果需要在外部進行訪問,就需要訪問方法了 set 和 get 方法。
4 private int age;//需要收集,但是不公開,age 就只需要一個set方法就可以了
5
6 //兩個參數的構造方法
7 public Student (String name,String sex){
8 this.name=name;
9 if(sex.equals("男")||sex.equals("女")){
10 this.sex = sex;
11 }
12 }
13 //普通方法
14 public void study(){
15 System.out.println(name+"在學習");
16 }
17 //性別設置器方法
18 public void setSex(String sex){
19 if(sex.equals("男")||sex.equals("女")){
20 this.sex = sex;
21 }else{
22 System.out.println("你的輸入不合法,請重新輸入..");
23 }
24 }
25 //性別訪問器方法
26 public String getSex(){
27 return sex;
28 }
29 //姓名設置器方法
30 public void setName(String name){
31 this.name = name;
32 }
33 //姓名訪問器方法
34 public String getName(){
35 return name;
36 }
37 //age設置器
38 public void setAge(int age){
39 this.age = age;
40 }
41 }
42 public class fengzhuang {
43
44 public static void main(String[] args) {
45 Student star = new Student("星星","性別");//性別 是不合法的操作
46 star.study();
47 System.out.println(star.getSex());//性別 null
48 }
49 }
繼承
特點:繼承父類的屬性和方法。 特性:方法的復寫(重寫) 單繼承(多層繼承)不是多繼承,c++才是多繼承一個子類N個父類。
java 中的繼承 和 OC中一樣。
繼承的作用:優化代碼,減少代碼的重復使用
A:B OC中繼承的寫法,java中如何表現繼承關系,用關鍵字 extends 表示繼承。
繼承中注意事項:
1.不要為了繼承而繼承,千萬不要為了節省代碼,任何關系都繼承,這樣就不倫不類了。
2.父類的私有成員變量是不能夠被繼承的。
3.父類的構造方法是不能被繼承的。
4.父類的私有方法不能被繼承。
5.子類調用自己的構造方法時,會默認調用父類中的無參構造方法。
6.子類不能夠繼承不在一個包中默認權限的成員變量。
為什麼會調用父類的構造方法?
子類在創建對象的時候初始化父類的變量。
技巧:畢竟這兩個屬性是從父類上面繼承下來的,初始化交給父類會好一點。。
super(name,sex);//一般由自己指定(定義),如果自己指定了下面的 super()就不可以調用了。
super();//調用的是父類的構造方法
this();//調用的是自己的構造方法

繼承代碼如下:
1 package 面向對象的三大特性;
2
3 class Person{
4 String name;//默認權限 friendly(友好的) private、public、protected
5 String sex;
6 Dog dog;//人和狗建立了 關聯關系 整體->部分
7 public void eat(){
8 System.out.println(name+"在吃飯");
9 }
10 }
11
12 //定於學生類繼承父類
13 class Student extends Person{
14 int age;
15 public void study(){
16 System.out.println(name+"在學習");
17 }
18 }
19
20 public class jicheng {
21
22 public static void main(String[] args) {
23 Student s = new Student();
24 s.name = "WKL";//name 自己沒有 父類有
25 s.age = 20;//age 自己有的
26 System.out.println(s.name+"今年"+s.age+"歲了..");
27 }
28 }
關聯關系(不是繼承):
1 class person{
2 String name;
3 String sex;
4 Dog dog;//人和狗建立了 關聯關系 整體->部分
5 public void eat(){
6 System.out.println(name+"在吃飯");
7 }
8 }
9
10 class Dog{
11 String name;
12 public void cry(){
13 System.out.println(name+"在叫");
14 }
15 }
16
17
18 public class jicheng {
19
20 public static void main(String[] args) {
21 person star = new person();
22 star.name = "星星";
23 Dog dog = new Dog();
24 dog .name = "小白";
25
26 star.dog = dog;//把狗這個對象 給 star的dog對象成員屬性
27 /*dog.cry();*/
28 star.dog.cry();//星星的狗在叫
29 star.dog = null;
30 star.eat();
31 }
32 }
super關鍵字(指向父類對象的引用空間)
作用:
1.當子類和父類存在同名的成員變量時,會先在子類裡面找默認有一個this(this.name),可以通過super來調用父類的成員變量(super.name)。
2.super可以用來調用父類的構造方法。
super使用的注意的地方:
1.用super調用父類構造方法,必須是構造方法中的第一個語句。
2.super只能出現在子類的方法或者構造方法中。
3.super 和 this 不能夠同時調用構造方法。(因為this也是在構造方法的第一個語句)
總結:super 和 this 的區別:
1.代表的事物不一樣:
this:代表所屬方法的調用者對象。
super:代表父類對象的引用空間。
2.使用前提不一致:
this:在非繼承的條件下也可以使用。
super:只能在繼承的條件下才能使用。
3.調用構造方法:
this:調用本類的構造方法。
super:調用的父類的構造方法
方法的復寫(重寫)
作用:父類的方法滿足不了子類的實現,這個時候就需要通過復寫(重寫)方法再實現父類的行為。
方法的復寫使用注意事項:
1.方法重寫的時候,必須存在繼承關系。
2.方法重寫的時候,方法名和形式參數 必須跟父類是一致的。
3.方法重寫的時候,子類的權限修飾符必須要大於或者等於父類的權限修飾符。( private < protected < public,friendly < public )
4.方法重寫的時候,子類的返回值類型必須小於或者等於父類的返回值類型。( 子類 < 父類 ) 數據類型沒有明確的上下級關系
5.方法重寫的時候,子類的異常類型要小於或者等於父類的異常類型。
方法的重載:方法名是一樣的,只是參數列表的個數,類型,順序不一樣。
多態(一個對象同種類型不同表現形態)
父類的引用類型指向了子類的對象。
多態使用注意事項:
1.多態情況下,父類 和 子類存在同名的成員變量,無論是靜態的還是非靜態的變量,默認訪問的是父類中的成員變量。
2.多態情況下,父類 和 子類存在同名的非靜態方法,訪問的是子類的非靜態方法。
3.多態情況下,父類 和子類存在同名的靜態方法,訪問的是父類的靜態方法。
4.多態情況下,不能訪問子類特有的屬性、方法。
5.多態滿足的條件:必須要有繼承關系。
總結:多態情況下,子類 和 父類如果存在同名的成員,訪問的都是父類,除了同名的非靜態變量訪問的才是子類。
java 編譯器編譯原理導致的。
編譯看左邊,運行不一定看右邊。
編譯看左邊的意思:java 編譯器在編譯的時候會檢測引用類型中含有指定的成員,如果沒有就會報錯。
1 package study;
2
3 abstract class Animal{
4 String name;
5 static String color = "動物色";
6
7 public abstract void run();
8
9 public void eat(){
10 System.out.println("這個是父類中的方法");
11 }
12 }
13
14 class Dog extends Animal{
15 static String color = "黃色";
16 //重寫父類中的方法
17 public void run(){
18 System.out.println(name+"用四條腿在跑步");
19 }
20 //重寫父類中的eat方法
21 public void eat(){
22 System.out.println("這個是子類中的方法");
23 }
24 }
25
26 class Fish extends Animal{
27
28 //重寫父類的方法
29 public void run(){
30 System.out.println(name+"在自由自在地游泳");
31 }
32 }
33
34 public class star {
35 public static void main(String[] args) {
36
37 Animal a = new Dog();//Animal 指針指向 Dog
38 a.name = "小黃";
39 a.run();
40
41 a.eat();
42 System.out.println(a.color);
43
44 // a = new Fish();//Animal 指針指向 Fish
45 // a.name = "小黃";
46 // a.run();
47 }
48 }
多態使用的場景:
1.多態可以用於做形式參數,可以讓方法接收更多的類型。
2.多態用於返回類型,可以返回更多的數據類型。
問題:
我返回的是圓的對象,不能用圓的引用變量來接收:返回的圖形 -> 圓的父類
基本數據類型的轉換:大的數據 -> 小的接收(強制轉換)
1 package study;
2
3 //需求1:定義一個方法可以接收任意類型 的圖形對象,求面積和周長。
4 //需求2:定於一個方法可以返回任意類型的圖形。
5 abstract class MyShape{
6 //定義兩個方法求面積和周長。
7 public abstract void getArea();
8 public abstract void getLength();
9 }
10
11 class Circle extends MyShape{
12 int r;
13 final double PI = 3.14;
14
15 //重寫父類中的方法
16 public void getArea(){
17 System.out.println("圓的面積");
18 }
19 public void getLength(){
20 System.out.println("圓的周長");
21 }
22 }
23
24 class Rect extends MyShape{
25
26 public void getArea(){
27 System.out.println("矩形的面積");
28 }
29 public void getLength(){
30 System.out.println("矩形的周長");
31 }
32 }
33
34 public class star {
35 public static void main(String[] args) {
36
37 //需求1:定義一個方法可以接收任意類型 的圖形對象,求面積和周長。
38 getAreaAndLength(new Circle());
39 getAreaAndLength(new Rect());
40
41 //需求2:定於一個方法可以返回任意類型的圖
42 MyShape a = getMyShape(0);//圓
43 /*getAreaAndLength(a);//在這裡拿到的是哪個型就計算哪個的面積和周長。*/
44
45 Circle c = (Circle)a;//引用數據類型的強制轉換
46 getAreaAndLength(c);//在這裡拿到的是哪個型就計算哪個的面積和周長。
47 }
48
49 public static void getAreaAndLength(MyShape ms){//這個參數拿到的是父類的對象,凡是屬於這個父類的都可以使用這個方法。如果是圓就只能接收圓的
50 ms.getArea();
51 ms.getLength();
52 }
53
54 public static MyShape getMyShape(int i){
55 if (i == 0) {
56 return new Circle();//圓
57 }else if (i == 1) {
58 return new Rect();//矩形
59 }
60 return null;
61 }
62 }