Java学习之面向对象

Java面向对象主要内容包括类和对象,面向对象的三大特性—封装、继承、多态。抽象类和接口。下面依次介绍。
一、类和对象

1、基本概念

类:是抽象的,是具有相同属性和方法一组对象的集合。类是一种自定义的数据类型

对象:是具体的,是描述客观事物的一个实体

2、类图

常用工具:Rose 、Visio

举例:        Dog

   +name:String    //属性名   类型

   -health:int     //+:public  -:private

   +print( ) : void   //方法名  返回值类型

3、类的方法

举例:public void play(){ }

private String getName(){return name}

无返回值 用void   有返回值 用int String等,必须使用关键字return

无参:方法名后()无参数    有参:方法名后()有参数

形参:定义的参数 方法后有{} 实参:调用的参数,方法后无{}

参数传递:要保证数据类型一致;顺序一致; 由实参单向传递给形参

4、方法调用

  • 在同类里无需创建对象直接调用,在其他类需要创建类对象。
  • Static静态方法,可以通过类名调用,无需创建类对象
  • 当输出一个对象时,会自动调用一个toString()方法

5、构造方法

作用:对象初始化   系统提供默认无参构造方法

举例:public Person(){this.name=”a”} 无参构造

public Person(String name){this.name=”a”}  有参构造

特点:方法名和类名相同;

   无返回值类型

   可以指定参数

6、方法重载

特点:同一个类中

   方法名相同

   参数个数或类型不同

   与返回值、访问修饰符无关

注意:构造方法的重载,由于此时系统不再提供默认无参构造方法,需要重新书写

7、成员变量、局部变量 

成员变量:在类中声明,在整个类中使用。有初始值 null

局部变量:在方法、代码体内声明,局部使用。无初始值

局部变量和成员变量同名的时候,局部变量具有更高的优先级

8、静态变量、实例变量

实例变量(也是成员变量)在类中声明,没有被static修饰。每创建一个实例,就会为实例变量分配一次内存。

静态变量(也是类变量)被static修饰的成员变量,通过类名直接访问会在内存中只有一个拷贝,优先占有空间,能被所有对象共享。

9、Java中栈和堆

堆内存用来存放由new创建的对象和数组,

栈内存用来存储基本类型的变量,常量,对象的引用变量。栈中的变量指向堆内存中的变量,又称为java的指针。

举例:int i=1;

String s = new String( “Hello World” );

变量i和s以及1存放在栈内存,而s指向的对象”Hello World”存放于堆内存。

10、this关键字

表示调用当前类中的成员变量和方法

注意:成员变量和局部变量同名,必须使用this关键字

在类的构造方法中,通过this调用重载的构造方法,必须是该构造方法的第一条语句

11、访问修饰符

访问级别从大到小:

public(任何地方)> protected(本类、本包、子类)

默认(本类、本包)> Private(本类)

Static修饰符:用来修饰成员变量、方法和代码块

静态变量和方法可以通过类名访问,静态代码块JVM加载类时自动执行
二、封装、继承、多态

1、封装

将类的状态信息隐藏在类的内部,不允许外部程序直接访问,但可以提供接口、方法来访问,防止被误操作。解决代码隐藏的问题

封装的体现:属性隐藏;包机制;

属性隐藏:修饰符改为private,设置getter/setter方法

包机制:类似创建文件夹,易于查找和管理。

定义包:package com.irunker.demo

导入包:import java.until.Date;

2、继承

子类继承父类的属性和方法,解决代码重用的问题

举例:public class Dog extends Pet{ }

特点:一个类只能有一个直接父类

   子类不能继承private修饰的属性和方法

   子类与父类是is-a关系

Object顶级父类:

所有java类都直接或间接的继承Object类

常用的方法:hashCode() getClass() equals() toString()  clone()

3、super、final关键字

super关键字

1、Super代表父类对象,可调用父类对象的属性和方法

2、在子类构造方法中调用且必须是第一句

3、无法访问private的成员

final关键字

(1)最终的意思,可以用于修饰类,方法,变量

(2) final修饰的类不能被继承。

final修饰的方法不能被重写。

final修饰的变量是一个常量。只能被赋值一次。

4、继承下构造方法调用规则

1、当子类构造方法没有用this\super显式调用,会自动调用父类无参构造方法

2、一旦父类使用带参构造方法,将会覆盖默认的无参构造方法。所以必须写无参构造方法

3、子类构造方法使用显式调用,则只调用的是父类有参构造方法,写法:super(name);

5、方法重写:

1、首先用super.方法的方式来保留父类的方法内容,可以继续添加其他方法内容

2、子类根据需求对从父类继承的方法进行重写,覆盖掉父类的方法。

3、构造方法不能重写

重写规则:

1、方法名、参数相同 2、父类声明、子类重写方法

区别:方法重载:同类、同名不同参    方法重写:不同类、同名也同参

6、多态

同一个引用类型,使用不同的实例,执行不同的操作

举例:Pet pet = new Dog()实例化一个子类对象。父类引用指向子类对象,子类完成向上转型,得到的对象可以直接调用子类方法

方法重写是实现多态的基础。解决代码的可扩展性问题

实现多态步骤:1、继承/实现接口   2、重写   3、向上转型

多态的应用:1、使用父类作为方法的形式参数 2、使用父类作为方法的返回值类型。静态绑定(引用成员变量、静态方法);动态绑定(引用重写后的方法)

7、向上转型与向下转型

向上转型:父类型 变量=new 子类型();  Pet pet=new dog();

父类引用变量指向子类对象,自动进行类型转换。

通过父类引用变量可以直接调用子类方法,但无法调用子类特有方法。

向下转型:子类型 变量=(子类型)父类型;  Dog dog=(Dog)pet;

父类类型转换为具体的子类类型,需要强制类型转换。

解决无法调用子类特有方法的问题。

为减少向下类型转换异常,使用instanceof运算符进行类型判断是否是是特定类的一个实例
三、抽象类与接口

1、抽象类与抽象方法

普通方法:

举例:public void work(){//方法体}

特点:有方法体、无abstract

抽象方法:  注意接口的抽象方法 可以不写public abstract

举例:public abstract void print();

特点:无方法体,有abstract;必须在抽象类里;必须在子类实现、否则子类必须被定义为抽象类

普通类:

修饰符 class 类名(){ … }

普通类可以被实例化(创建对象)

抽象类:

修饰符 abstract  class 类名{ }

1、可以有非抽象的构造方法,在子类实例中调用;但一定没有抽象构造方法,也没有抽象静态方法  public abstract Base(){}  X

2、抽象类里一般有抽象方法,也可以没有抽象方法。抽象类不允许实例化(创建对象),接口也是一样。如:Pet pet=new Pet();  X

2、接口

用interface修饰的一个不可实例化的类

创建:

public interface usbInterface extends Io1,Io2{//接口继承父接口

void sevice();  //抽象方法,默认是的abstract、public的,一般不写 }

实现:

public class MyClass extends Base implements Io1,Io2{//继承父类实现接口 }

特性:

接口没有构造方法,不可被实例化,常作为类型使用

一个类必须实现接口的所有方法,除非这个类是抽象类;接口可以继承多个接口

接口中的变量都是静态变量(public static final),必须显式初始化

接口的使用:

接口中的成员变量:默认都是public static final的,必须显式初始化

接口中的方法:默认都是public abstract的

使用原则:

接口做系统和外界的交互、

接口一旦制定,不可修改

抽象类可以完成部分功能实现

3、抽象类与接口

类似于   鸟-抽象类 鸟叫-接口

1、抽象类只能单继承,接口可以多实现

2、抽象类被继承是”is a”关系;  接口被实现是”like a、has a “关系

3、抽象类中定义的是继承体系中的共性功能。接口中定义的是继承体系中的扩展功能。

4、抽象类有构造方法,可以是变量、非抽象方法。接口成员变量是常量,都是抽象方法,却没有构造方法。

4、面向对象设计的原则

1、摘取代码中变化的行为,形成接口

2、多用组合,少用继承

3、针对接口编程,不依赖于具体的实现

4、针对扩展开放,针对改变关闭

5、关于is-a has-a ,like-a

  • is-a,顾名思义,是一个,代表类的继承关系。子类继承父类

如果A is-a B,那么B就是A的父类。

一个类完全包含另一个类的所有属性及行为。

Ag 狗是一种动物;猫是一种动物

  • has-a,顾名思义,有一个,代表从属关系。对象从属于类

如果A has a B,那么B就是A的组成部分。

同一种类的对象,通过它们的属性的不同值来区别。

Ag 狗有一个名字  计算机有一个操作系统。

  • like-a,顾名思义,像一个,代表组合关系。

如果A like a B,那么B就是A的接口。

新类型有老类型的接口,但还包含其他函数,所以不能说它们完全相同。

Ag 计算机有一个USB接口  空调有一个实现加热的接口

6、异常处理

常见异常:

NumberFormatException数字格式转换异常

InputMismatchException:数据类型不匹配异常

Arithmetic Exception:算数异常(/by zero)

Nullpointer Exception:空指针异常(访问null对象成员)

ClassCastException:对象强制类型转换出错

JAVA异常处理机制:

1、Try-catch

2、Try-catch-finally finally代码块总被执行,除非执行System.exit(1)才中断。即使出错,遇到return,也要完成finally代码块的操作

3、try-catch-catch多重catch: 有顺序的(先子类后父类Exception)

4、throw抛出异常,位于方法体内

5、throws声明一个或多个异常,位于方法参数列表后面  方式:调用者处理异常,继续抛出异常

6、自定义异常     SexExcepetion extends Exception 
四 、相关代码

Code    View Print
  1. package com.hfxt.demo03;
  2. public class School {
  3.     private String name;
  4.     private Printer printer;
  5.     public School(){}
  6.     public School(String name, Printer printer) {
  7.         super();
  8.         this.name = name;
  9.         this.printer = printer;
  10.     }
  11.     public void setPrinter(Printer printer) {
  12.         this.printer = printer;
  13.     }
  14.     public void printing(String content){
  15.         if(printer==null){
  16.             System.out.println(“暂时没有配置打印机”);
  17.         }else{
  18.             printer.print(content);
  19.         }
  20.     }
  21. }
  22. package com.hfxt.demo03;
  23. public class Printer {
  24.     private String brand;
  25.     private double price;
  26.     public Printer(){}
  27.     public Printer(String brand, double price) {
  28.         super();
  29.         this.brand = brand;
  30.         this.price = price;
  31.     }
  32.     public void print(String content){
  33.         System.out.println(content+“ ”+this.brand+“ ”+this.price);
  34.     }
  35. }
  36. package com.hfxt.demo03;
  37. public class ColorPrinter extends Printer{
  38.     public ColorPrinter() {
  39.         super();
  40.         // TODO Auto-generated constructor stub
  41.     }
  42.     public ColorPrinter(String brand, double price) {
  43.         super(brand, price);
  44.         // TODO Auto-generated constructor stub
  45.     }
  46.     @Override
  47.     public void print(String content) {
  48.         System.out.println(“彩色打印”);
  49.         super.print(content);
  50.     }
  51. }
  52. package com.hfxt.demo03;
  53. public class BlackPrinter extends Printer{
  54.     public BlackPrinter() {
  55.         super();
  56.         // TODO Auto-generated constructor stub
  57.     }
  58.     public BlackPrinter(String brand, double price) {
  59.         super(brand, price);
  60.         // TODO Auto-generated constructor stub
  61.     }
  62.     @Override
  63.     public void print(String content) {
  64.         System.out.println(“黑白打印”);
  65.         super.print(content);
  66.     }
  67. }
  68. package com.hfxt.demo03;
  69. public class Test {
  70.     public static void main(String[] args) {
  71.         School school = new School();
  72.         school.printing(“123”);
  73.         /*Printer printer = new BlackPrinter(“ph”, 3);
  74.         school.setPrinter(printer);
  75.         school.printing(“123”);
  76.         
  77.         printer=new ColorPrinter(“canon”, 3.5);
  78.         school.setPrinter(printer);
  79.         school.printing(“321”);*/
  80.         Printer printer = new BlackPrinter(“ph”3);
  81.         printer.print(“abc”);
  82.         printer=new ColorPrinter(“canon”3.5);
  83.         printer.print(“123”);
  84.     }
  85. }
  86. package practice;
  87. /**
  88.  * 
  89.  * @author Visant
  90.  *定义形参,调用实参;值传递、引用传递;传递方向:实参到形参,单向的;
  91.  *注意引用传递:引用堆地址,结果随变量值变化而变化
  92.  *无参、有参;有无返回值方法的学习
  93.  *引用数据类型:String、自定义类、接口、数组
  94.  */
  95. public class Demo3 {
  96.     //public void work(){}//()里无参数就是  无参
  97.     public void work(String contect){}//()里有参数就是  有参
  98.     public String work(){return “理想”;}//方法前不是void 说明是带返回值方法
  99.     //public void work(){}//不带返回值的方法
  100. //调用实参 值传递
  101. /*  public static void fun(int t){//定义 形参    t=a;
  102.         System.out.println(“1t:”+t);//t=1
  103.         t=2;
  104.         System.out.println(“2t:”+t);//t=2
  105.     }
  106.     public static void main(String[] args) {
  107.         
  108.         int a=1;
  109.         System.out.println(“1a:”+a); //a=1
  110.         fun(a);//调用实参 值传递
  111.         System.out.println(“2a:”+a);//不存在位置传递,自然a=1
  112.     }*/
  113. //调用实参 引用传递
  114. /*  public static void fun(int []t){//定义 形参  t[0]=a[0] a[0]堆地址给了变量t
  115.         System.out.println(“1—t[0]:”+t[0]);//t[0]=1
  116.         t[0]=2;
  117.         System.out.println(“2—t[0]:”+t[0]);//t[0]=2  t[0]占用了原来a[0]的位置
  118.     }
  119.     public static void main(String[] args) {
  120.         
  121.         int []a=new int[]{1};
  122.         System.out.println(“1—a[0]:”+a[0]);//a[0]=1
  123.         fun(a);//调用实参 引用传递
  124.         System.out.println(“2—a[0]:”+a[0]);//a[0]此时值=t[0]的值  2
  125.     }*/
  126. //调用实参 值传递【注意传递的是a[0],也就是一个值】
  127. /*  public static void fun(int t){//定义 形参
  128.         t=2;
  129.     }
  130.     public static void main(String[] args) {
  131.         
  132.         int []a=new int[]{1};
  133.         fun(a[0]);//调用实参 值传递
  134.         System.out.println(a[0]);
  135.     }*/
  136. }

猜你喜欢

转载自blog.csdn.net/w252064/article/details/79926106