java进阶(面向对象编程)

类与对象普通变量对象变量(管理者)类是规范,对象是实体对象 = 属性(数据)+函数(操作) = 成员变量+成员函数封装:把数据和对数据的操作放在一起(外部的操作保护内部的数据)定义类创建对象new VendingMachine();VendingMachine v = new VendingMachine();对象变量是对象的管理者运算符.成员变量和成员函数函数...
摘要由CSDN通过智能技术生成
  • Java程序的三个阶段
    1. Type
    2. Class
    3. Runtime
  • Java类的3个结构
    1. Field
    2. Constructor
    3. Method

黑马程序员部分

project(工程) > (src) > package(包) > class(类) > object(对象)> 成员(变量,函数和内部类)

一个类中可以有成员变量、方法,还可以有内部类。内部类实际上是它所在类的成员。内部类最重要的特点就是能够访问外部类的所有成员

面向对象编程三大特性
封装,继承,多态

Java中的变量:
1.成员变量(实例变量,属性)
2.本地变量(局部变量)
3.类变量(静态属性)

byte 字节 就是2个16进制数 00到FF 8位
1024 byte = 1k b

Java基本类型占用的字节数:
1字节: byte , boolean
2字节: char,short
4字节: int , float
8字节: long , double
附录:
编码:
数字都是一个1字节
GBK: 中文2字节
UTF-8: 中文通常3字节,在拓展B区之后的是4字节

int默认10进制,数字前面加0b表示2进制,0x表示16进制

final关键字

  • 可以用来修饰一个类,方法,局部变量,成员变量

类与对象

普通变量
对象变量(管理者)

  • 类是规范,对象是实体
  • 对象 = 属性(数据)+函数(操作) = 成员变量+成员函数
  • 封装:把数据和对数据的操作放在一起(外部的操作保护内部的数据)
  • 定义类
  • 创建对象
new VendingMachine();
VendingMachine v = new VendingMachine();

对象变量是对象的管理者
运算符.

  • 成员变量和成员函数
    • 函数要通过对象来调用
    • this是成员函数固有的本地变量,他表示调用这个函数的那个对象
    • 在成员函数内部可以直接调用自己(this)的其他成员函数
    • 定义在函数内部的是本地变量,生存期和作用域都在函数内部
    • 成员变量的生存期是对象的生存期,作用域是类内部的成员函数
  • 对象初始化
    • java会给未初始化的成员变量赋0值(广义,boolean给false,对象变量给None等)
    • 构造函数(不能有返回类型)
      • 如果有一个成员函数的名字和类的名字完全相同,构造对象时候被自动调用,这个函数则是构造函数
      • 不能有返回类型
      • 创建对象先进构造函数的头,在去定义成员变量,再进构造函数体
      • 构造函数可以有多个,只要参数表不同即可(可以接受参数,也可以不接受参数)。通过this()可以调用其他构造函数(只能使用一次)。还可以根据创建对象时给的参数来选择调用哪个构造函数。(称为重载)
      • 重载
        一个类里的同名但参数表不同的函数构成了重载关系

对象交互

类的首字母大写

  • 对象的识别
  • 对象交互
    多个对象可组成一个对象

tip(%占位符,%d整数%f小数)

  • 封闭的访问属性
    • 所有的成员都可以设定访问属性
    • private 成员为类私有,只有成员函数和成员变量可以访问
      私有是针对类而不是针对对象,即同一类的其他对象都可以访问
  • 开放的访问属性
    • public表示任何人都可以访问他
    • 没有public或者private限制的,我们称为friendly,即同一个包内的可以访问。
    • protect在继承中再提
    • class是public表示任何地方都可以用该类的定义来定义一个变量

编译单元(.java文件):一个编译单元最多只能有一个class是public

  • 包(管理机制)

    • 在一个目录底下的所有编译单元(源代码文件),包的名字就是目录的名字。
    • 如果不import其他包,想要用里面的类就得给全名,比如display.Display。import display.*不推荐,防止和本地包的类重名
    • 包的里面还可以包含包,如java.util.Scanner
  • 类变量

public class Display{
   
   private static int step = 1;
}
- d1.step = d2.step = Display.step
- 可通过对象访问类变量,但是类变量不属于对象

- 类函数(static函数)
属于类的函数,可以访问其他类函数

public class Display{
   
   public static viod main = {
   };
}

static成员的初始化和对象的创建没关系

对象容器

  • 泛型容器类

    • 容器的两个类型
      1. 容器的类型(ArrayList)
      2. 元素的类型(String)
    • ArrayList < String > (ArrayList of String)
      • 创建一个该类对象notes后可用的操作
        • notes.size() 查看有多少条
        • notes.get(index) 获得相应索引的元素
        • notes.add(location,element) 相应位置加元素
        • notes.remove(index) 返回remove的元素
        • notes.toArray(a) 将内容填充到数组a中
    • 可使用for-each循环
  • 对象数组

    对象不存在则为null

    • String[] 里面的元素是String类的管理者(和基础类型数组的区别)
    • 可定义String a = null
    • length()可获得数组的长度
    • for-each循环,以下代码是可实现的(和基础类型数组的区别)
    //对字符串数组a而言
    String[] a = new String[10];
    for (String k : a){
         
    	k = "good";
    }
    
  • 集合容器

    • HashSet< String >
    • 无顺序,元素不能重复
    • toString()方法使得该容器可以直接输出
    class Value{
         
    	public String toString(){
         return ""+i;}
    }
    
  • Hash表

    • HashMap<Interger,String>
    private HashMap<Interger,String> coinnames = new HashMap<Interger,String>();
    coinnames.put(key,value)
    coinnames.keySet() //得到key表
    coinnames.keySet().size()
    coinnames.get(index)
    

继承(Inherited)

基于已有的设计创造新的设计,就是面向对象程序设计的继承
代码复制是代码质量不良的表现,不好维护

  • 基础派生出其他类的那个类叫做父类(超类,基类),派生出来的叫子类。
    Java用关键字extends来表示这种继承/派生关系
    class ThisClass extends SuperClass{//…}
  • 子类的对象对可以看做是父类的对象。
  • Java只允许单继承,即一个类只能有一个父类
  • 父类所有的成员都会被子类继承,都是存在的,都是可能可以用的(还要考虑访问权限)

public:所有人都能访问
protected:包内和包外的子类可以访问
缺省:包内可以访问
private:只有类自己可以访问

访问权限关系

  • public的成员直接成为子类的public的成员,protected的成员也直接成为子类的protected的成员。Java的protected的意思是包内和子类可访问,所以它比缺省的访问属性要宽一些。而对于父类的缺省的未定义访问属性的成员来说,他们是在父类所在的包内可见,如果子类不属于父类的包,那么在子类里面,这些缺省属性的成员和private的成员是一样的:不可见。父类的private的成员在子类里仍然是存在的,只是子类中不能直接访问。我们不可以在子类中重新定义继承得到的成员的访问属性。如果我们试图重新定义一个在父类中已经存在的成员变量,那么我们是在定义一个与父类的成员变量完全无关的变量,在子类中我们可以访问这个定义在子类中的变量,在父类的方法中访问父类的那个。尽管它们同名但是互不影响。
  • 子类通过super()来调用父类的构造函数,从而构造自己的成员变量。

构造子类对象时,先进构造函数头,再进父类的构造函数初始化,再进入定义初始化,再去做构造函数的剩下部分。
可以理解为:
父类的定义初始化和构造初始化做完后,再做子类的定义和构造初始化
没有super()会默认去找父类中没有参数的构造器,如果有super(),就根据super()中的参数来寻找父类的构造函数。

  • 在构造一个子类的对象时,父类的构造方法也是会被调用的,而且父类的构造方法在子类的构造方法之前被调用。在程序运行过程中,子类对象的一部分空间存放的是父类对象。因为子类从父类得到继承,在子类对象初始化过程中可能会使用到父类的成员。所以父类的空间正是要先被初始化的,然后子类的空间才得到初始化。在这个过程中,如果父类的构造方法需要参数,如何传递参数就很重要了。

  • 子类如果有函数和父类同名,使用super.func()来调用父类的那个函数(父类这个函数是可访问时)

  • 父类item和子类DVD

//Item.java
package database;

public class Item {
   
	private String title;
	private int playingTime;
	private boolean gotIt;
	private String comment;
		
	public Item(String title, int playingTime, boolean gotIt, String comment) {
   
		this.title = title;
		this.playingTime = playingTime;
		this.gotIt = gotIt;
		this.comment = comment;
	}

//	public void setTitle(String title) {
   
//		this.title = title;
//	}
	
	public void print() {
   
		System.out.print(title+" ");
	
	}
	public static void main(String[] args){
   
	}
}
//DVD.java
package database;

public class DVD extends Item {
   
	private String director;
	
	public DVD(String title,String director,int playingTime, boolean gotIt, String comment) {
   
		super(title,playingTime,gotIt,comment);
		this.director = director;
	}
	
	public void print() {
   
		System.out.print("DVD: ");
		super.print();
		System.out.print(director);
	}
	
	public static void main(String[] args){
   
		DVD dvd = new DVD("lovelyy","wjj",120,false,"...");
		dvd.print();
	}
}

多态

  • 子类和子类型
    • 类定义了类型
    • 子类定义了子类型
    • 子类的对象可以被当做父类的对象来使用
      1. 赋值给父类的变量
      2. 传递给需要父类对象的函数
      3. 放进存放父类对象的容器里
  • 多态变量(声明(静态)类型,动态类型)
    • java的对象变量是多态的,它们能保存不止一种类型的对象
    • 它们可以保存的是声明类型的对象,或者声明类型的子类的对象
    • 当把子类的对象赋给父类的变量的时候,就发生了向上造型
  • 造型cast
    • 子类的对象可以赋值给父类的变量(向上造型)
      注意!java中不存在对象对对象的赋值,是对象的管理者同时管理(或者说管理权限的变化)
    • 父类的对象不能直接赋值给子类的变量(除非Person p = (Person)obj这样)
  • 用括号围起来的类型放在值的前面称为造型
  • 对象本身没有发生任何变化,所以不是“类型转换(int i = (int)10.2)”,要区分(虽然英语的单词都是cast)!
  • 运行时有机制来检查这样的转化是否合理(ClassCastException)
  • 向上造型
    • 拿一个子类的对象,当做父类对象来用
      对于DVD对象dvd,Item类型变量i
      i = dvd
    • 向上造型是默认的,不需要运算符
    • 向上造型是安全的
  • 向下造型例子
    对于DVD变量d,Item类对象v
    d = (DVD) item;
    需要v被指向一个DVD这个子类对象。如果没有指向,那在编译时时没问题的,但是运行时会产生错误
  • 多态

    • 函数调用的绑定(对多态变量而言(如item))
      • 当通过对变量对象调用函数时,调用哪个函数这件事情叫做绑定
        1. 静态绑定:根据变量的声明类型来决定
        2. 动态绑定:根据变量的动态类型来决定(java都是动态绑定)
      • 在成员函数中调用其他成员函数也是通过this这个对象变量来调用的(看做动态绑定)
    • 覆盖(override)
      • 子类和父类存在名称和参数表完全相同的函数,这一对函数构成覆盖关系
      • 通过父类的变量调用存在覆盖关系的函数时,会调用变量当时所管理的对象所属的类的函数
  • Object类
    java是单根结构,所有的类都是Object类的子类,Object类是root类

    • Object类的函数
      Obeject o = new Object();
      o. 来查看有哪些函数
      • toString() (如果不覆盖(override),默认Object类的toString()会输出package.Class@e76cbf7)
        如果对一个对象进行字符串加法,会寻找是否有这个方法,如果有就能进行字符串的加法
      • equals()(默认来查看是否管理的是同一个对象)
        可覆盖(override)来设置该函数为:查看某个成员变量是否相等
      @override
      public boolean equals(Object obj){
             
      	CD cc = (CD)obj;
      	return artist.equals(cc.artist);
      }
      
    • @Override表示(为了告诉编译器)以下部分的函数,是覆盖了父类的函数。和父类的函数具有完全相同的函数签名(函数原型):函数的名字和函数的参数表都相同,而且都是public(权限也不能变)
  • 例子:dome的新媒体类型

    • 代码的可拓展性,与可维护性不同(可维护性是易于修改,可拓展性是易于增加)
    • 子类的底下还可以再派生子类,生成更深的继承关系

设计原则

  • 代码复制问题
    编写函数方法来解决
  • 封装
    通过封装来降低耦合(通过接口来解耦)
    • 类和类之间的关系称为耦合
      高耦合的表现:两类都有大量的代码和出口相关,大量使用另外一个类的成员变量
    • 耦合越低越好

String是一个immutable(不可修改)的对象,当需要很多复杂的字符串操作来产生一个结果字符串时,为防止系统开销过大,可使用StringBuffer对象,这是一个可以不断修改的对象。最后用toString()产生一个String对象就可以

  • 可拓展性
    • 通过接口来实现聚合
    • 通过容器来实现灵活性
      • Hash表
  • 框架加数据
    • 以框架+数据来提高可拓展性
      • 命令的解析是否可以脱离if-else
      • 定义一个Handler来处理命令
      • 用Hash表来保存命令和Handler之间的关系
    • 城堡游戏
//Game(Main).java
package 
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值