面向对象
面向对象
什么是面向对象
-
面向对象编程本质:以类的方式组织代码,以对象的组织封装数据
-
三大特性:
封装
继承
多态
构造器
-
定义
(1)和类名相同(无参构造)
(2)没有返回值
-
作用:
(1)new本质在调用构造方法
(2)初始化对象的值
-
注意点:
(1)定义有参构造之后,如果想使用无参构造,显示的定义一个无参构造
-
this. =
this.name = name;
this.age = age;
-
举例:
public class Person {
//一个类即使什么都不写,他也会存在一个方法
//显示定义构造器
String name;
//实例化初始值
//无参构造
//1.使用new关键字必须有构造器,本质是在调用构造器
//2.用来初始化值
public Person(){
this.name = "姜皓文";
}
//有参构造:一旦定义了有参构造,无参构造就必须显示定义
public Person(String name){
this.name ="wang";
}
}
/*
//new 实例化了一个对象
//Person person = new Person(); //调用无参构造
Person person = new Person("wang"); //调用有参构造
System.out.println(person.name);
*/
创建对象内存分析
封装
-
程序设计要求“高内聚,低耦合”,高内聚:类的内部操作数据细节有自己完成,不容许外人插手。
低耦合:进暴露少量的方法给外部使用
-
属性私有:get,set
-
作用:
(1)提高程序的安全性,保护数据
(2)隐藏代码的实现细节
(3)统一接口(get,set)
(4)系统可维护增加了
4.举例:
//类 private 私有
public class Students {
//属性私有
private String name; //名字
private int id; //学号
private String sex; //性别
private int age; //年龄
//提供一些可以操作这些属性的方法
//提供一些public 的get set 方法
//get 取值
public String getName(){
return this.name;
}
//set 存值
public void setName(String name){
this.name = name;
}
//睡觉()
//说话() //方法
public void setAge(int age) {
if(age>120 || age<0){ //不合法
this.age = 3;
}else{
this.age = age;
}
}
public int getAge() {
return age;
}
}
//调用上面的类
public class Aplication {
public static void main(String[] args) {
Students s = new Students();
s.setName("王玉");
System.out.println(s.getName());
s.setAge(555); //不合法
System.out.println(s.getAge());
}
}
继承
-
继承的本质是对某一批类的抽象,实现对现实世界最好的建模
-
java中只有单继承,没有多继承(一个孩子只会有一个爸爸,一个爸爸会有多个孩子)
-
’extends‘,意思为扩展,子类是父类的扩展;
-
public:公有的 protected :受保护的 default: 默认的 private:私有的
-
在java中所有的类,都默认直接或间接的继承Object
-
final不能用作继承
public class Student extends Person//报错
{}
public final class Person {}
super
-
super注意点:
(1)super调用父类的构造方法,必须在构造方法的第一个!;
(2)super只能出现在子类的方法和构造方法中!;
(3)super和this不能同时调用构造方法!;
-
VS this
代表的对象不同:
super:代表父类的引用
this:代表引用本身的这个对象
前提:
super:只能在继承条件下使用
this:没有继承也可以使用
构造方法:
super():父类的构造
this():本身的构造
//Person 父类 人
public class Person {
protected String name = "王雨萌";
public Person(){
System.out.println("Person无参构造了");
}
public void print(){
System.out.println("person");
}
}
//学生 is 人 : 派生类,子类
//子类继承了父类,就会拥有父类的所有属性和方法
public class Student extends Person{
private String name = "姜浩文";
public Student(){
//隐藏代码调用了无参构造
super();//调用父类的构造器,必须要在子类的上面
System.out.println("Student无参构造了");
}
public void print(){
System.out.println("strudent");
}
public void test(String name){
System.out.print(this.name);//姜浩文
System.out.print(name);//爱
System.out.print(super.name);//王雨萌
}
public void test1(){
print();//student
this.print();//student
super.print();//super
}
}
//一个项目只能存在一个main方法
public class Aplication {
//调用上面的类
public static void main(String[] args) {
Student s = new Student();
s.test("爱");
s.test1();
}
}
方法重写
-
子类重写父类的方法
-
前提:
(1)需要有继承的关系;
(2)方法名必须相同;
(3)参数列表必须相同;
(4)修饰符:范围可以扩大但不能缩小; public>protected>default>private
(5)抛出异常:范围,可以被缩小但不能扩大; ClassNotFoundException--->Exception(大)
-
重写,子类的方法和父类的方法必须一致,方法体也不能相同(重写都是方法的重写,和属性无关)
-
为什么需要重写:
父类的功能,子类不一定需要,或者不一定满足!
//继承
public class B {
public void test(){
System.out.println("B=>test()");
}
}
//重写都是方法的重写,和属性无关
public class A extends B {
//Override 重写
//一个项目只能存在一个main方法
public class Aplication {
public static void main(String[] args) {
//静态的方法和非静态的方法区别很大
//静态方法: //方法的调用,只和左边定义的数据类型有关
//非静态方法:重写
A a = new A();
a.test();
//父类的引用指向了子类
B b = new A();//子类重写了父类的方法
b.test();
}
}
多态
-
注意事项
(1)多态是方法的多态,属性没有多态
(2)父类和子类之间要存在联系,否则转换异常! Class CastException!
(3)存在条件:继承关系,方法需要重写
-
不能重写
(1)static 方法,属于类,它不属于实例
(2)final 常量
(3)private 方法;
-
定义:即同一方法可以根据发送不同的对象,而采用多种不同的行为方式
public class Person {
public void test(){
System.out.println("test");
}
}
public class Student extends Person{
//一个项目只能存在一个main方法
public class Aplication {
public static void main(String[] args) {
//一个对象的实际类型是确定的
//new Student();
//new Person();
//可以指向的引用类型就不确定了:父类的引用指向子类
//Student能调用的方法,都是自己的或者是继承父类的方法
Student s1 = new Student();
//Person 父类型 ,可以指向子类,但是不能调用子类独有的方法
Person s2 = new Student();
Object s3 = new Student();
//对象能执行哪些方法,主要是看对象左边的类型,和右边关系不大
s2.test(); //子类重写了父类的方法,执行了子类的方法
s1.test();
}
}
instanceof
/*//Object>Person>Student
Object object = new Student();
//Object>Person>Teacher
Object o = new Teacher();
//Object>String
Object o1 = new String();
System.out.println(object instanceof Student);//true
System.out.println(object instanceof Person);//true
System.out.println(object instanceof Object);//true
System.out.println(object instanceof Teacher);//false
System.out.println(object instanceof String);//false
System.out.println(o instanceof Teacher);//true
System.out.println(o1 instanceof String);//true
*/
类型转换
-
格式:
((强制转化对象)变量名).方法名(强制转换的方法名)
-
特点:
(1)父类引用指向子类的的对象
(2)把父类转化为子类,向下转换:强制转化,,,可能会丢失一些方法
(3)把子类转化为父类,向上转换
(4)方便方法的调用,减少重复的代码!
public class Aplication {
public static void main(String[] args) {
Person person = new Student();
//((强制转化对象)变量名).方法名(强制转换的方法名)
((Student)person).run();
//类型之间的转化
Student student = new Student();
student.run();
//子类转化为父类,可能会丢失一些方法
Person person = student;
//person.run();
}
}
static
public class Person {
//2.赋初始值
{
System.out.println("匿名代码块");
}
//1.只执行一次
static {
System.out.println("静态代码块");
}
//3
public Person(){
System.out.println("构造器");
}
public static void main(String[] args) {
Person person = new Person();
System.out.println("==============");
Person person1 = new Person();
}
}
/*静态代码块
匿名代码块
构造器
==============
匿名代码块
构造器
*/
/*{
//代码块(匿名代码块)
}
static{
//静态代码块
}*/
public class Student {
private static int age; //静态变量 多线程
private int score; //非静态变量
public void run(){
go();
}
public static void go(){
}
//动态方法可以调用静态方法,反之不成立
public static void main(String[] args) {
go();
//run(); //报错
Student student = new Student();
student.run();
System.out.println(Student.age);
//System.out.println(Student.score);
System.out.println(student.age);
System.out.println(student.score);
}
}
//静态导入包
import static java.lang.Math.random;
import static java.lang.Math.PI;
public class Import {
public static void main(String[] args) {
//System.out.println(Math.random());
System.out.println(random());
System.out.println(PI);
}
}
抽象
-
通过abstract关键词继承
//abstract 抽象类 类 extends 单继承 (接口:多继承)
public abstract class Demo5 {
//约束 有人帮我们实现
//abstract 抽象方法 只有方法名字,没有方法的实现!
public abstract void go();
//1.不能new这个抽象类,只能靠这个子类去实现:约束!
//2.抽象类里能定义非抽象方法,抽象方法必须在抽象类中
}
接口
作用
-
起到约束作用
-
在接口内定义一些方法,让不同的人去实现~
-
接口中的所有定义的方法其实都是抽象的 ~~ 默认的是 public abstract方法
-
常量~ 默认的是public static final
-
接口不能被实例化,接口中没有构造方法
-
interface ~~ 定义接口的关键字
-
接口中只有方法的定义,没有方法的实现
-
implements可以实现多个接口
-
实现了接口的类。就必须重写接口中的方法
-
//interface 定义接口的关键字 接口都需要有实现类
//接口中只有方法的定义,没有方法的实现
public interface UserServer {
//常量~ 默认的是public static final
int age = 99;
//接口中的所有定义的方法其实都是抽象的 public abstract
void add(String name);
void delete(String name);
void update(String name);
void query(String name);
}
//抽象类 extends
//类 可以实现接口,通过implements接口
//实现了接口的类。就必须重写接口中的方法
//多继承~利用接口实现多继承~
public class UserServerImpl implements UserServer,Timer{
内部类
-
成员内部类
//Outer 外部类
public class Outer {
private int age =12 ;
public void out(){
System.out.println("这是一个外部类");
}
//Inner内部类
public class Inner{
public void in(){
System.out.println("这是一个内部类");
}
//获得外部私有属性~私有方法
public void getAge(){
System.out.println(age);
}
}
}
-
静态内部类
-
局部内部类
//Outer 外部类
public class Outer {
//局部内部类
public void method(){
class In{
public void Inner(){
}
}
}
}
-
匿名内部类
public class Test {
public static void main(String[] args) {
new Apple().eat();
/*new UserServer(){
@Override
public void ho() {
// TODO Auto-generated method stub
}
};*/
}
}
class Apple{
public void eat(){
System.out.println("吃苹果");
}
}
/*interface UserServer{
public void ho();
}*/
-

浙公网安备 33010602011771号