面向对象
面向对象(OOP)
面向对象编程的本质是:以类的方式组织代码,以对象的方式组织(封装)数据。
-
三大特性:
封装
继承
多态 -
值传递和引用传递
例:值传递
public class Demo2 {
public static void main(String[] args) {
int a = 1;
System.out.println(a);// 1
Demo2.change(a);
System.out.println(a);// 1
}
public static void change(int a){
a = 10;
}
}
例:引用传递
public class Demo1 {
public static void main(String[] args) {
Person person = new Person();
System.out.println(person.name);//null
Demo1.change(person);
System.out.println(person.name);// Tom
}
public static void change(Person person){
//person是一个对象:指向的———>Person person = new Person();这是一个具体的人,可以改变属性!
person.name="Tom";
}
}
class Person{
String name;
}
类和对象的关系
- 类是一种抽象的的数据类型,它是对某一类事物整体描述和定义,但并不能代表某一个具体的事物。
- 对象是抽象概念的具体实例。
创建和初始对象
- 使用new关键字创建对象;
- 使用new关键字创建的时候,除了分配内存空间,还会给创建好的对象进行默认的初始化以及对类中的构造器的调用。
- 类中的构造器也称为构造方法,是在进行创建对象时必须调用的。
- 构造器的两个特点:
1.必须和类的名字相同。
2.必须没有返回类型,也不能写void。
例
package com.zzh.oop.demo;
// 一个项目应该只有一个main方法
public class Application {
public static void main(String[] args) {
Person person = new Person("Tom",10);
System.out.println(person.name);
}
}
package com.zzh.oop.demo;
public class Person {
// 一个类什么都不写也会存在一个默认构造器
String name;
int age;
//1.使用new关键字,本质是在调用构造器
//2.用来初始化值
//无参构造
public Person(){
//this.name = "Tom";
}
//有参构造:一旦定义了有参构造,必须显示定义无参构造。
public Person(String name){
this.name = name;
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
//alt + insert 生成构造器
}
封装
- 高内聚、低耦合。高聚内:类的内部数据操作细节自己完成,不允许外部干涉;低耦合:仅暴露少量的方法外部使用。
- 封装(数据的隐藏),通过接口访问而禁止直接操作。
- 属性私有,get/set方法
例:
package com.zzh.oop.demo1;
public class Application {
public static void main(String[] args) {
Student student = new Student();
student.setName("Tom");
student.setSex("男");
System.out.println(student.getName()+":"+student.getSex());
}
}
package com.zzh.oop.demo1;
public class Student {
//属性名私有
private String name;
private int id;
private String sex;
//提供一些public的get,set方法
// Alt + Insert
// get获得这个数据
public String getName(){
return this.name;
}
public int getId() {
return id;
}
public String getSex() {
return sex;
}
// set 给这个数据设置值
public void setName(String name) {
this.name = name;
}
public void setId(int id) {
this.id = id;
}
public void setSex(String sex) {
if(sex=="男" || sex =="女" ){
this.sex = sex;
}else {
this.sex = "null";
}
}
}
继承
-
继承的本质是对一批类的抽象,从而实现对现实世界更好的建模。
-
关键词 extends,子类是父类的扩展。
-
Java中只有单继承,没有多继承。继承是类和类之间的一种关系,除此之外类和类之间的关系还有依赖、组合、聚合等。
私有的东西无法被继承。 -
object类是所有类的父类。
Ctrl + H
查看类之间的关系。 -
final 修饰的类无法被继承
-
super
package com.zzh.oop.demo1;
public class Student {
//属性名私有
private String name;
private int id;
private String sex;
//提供一些public的get,set方法
// Alt + Insert
public Student() {
System.out.println("我是学生");
}
public void print(){
System.out.println("父类");
}
// get获得这个数据
public String getName(){
return this.name;
}
public int getId() {
return id;
}
public String getSex() {
return sex;
}
// set 给这个数据设置值
public void setName(String name) {
this.name = name;
}
public void setId(int id) {
this.id = id;
}
public void setSex(String sex) {
if(sex=="男" || sex =="女" ){
this.sex = sex;
}else {
this.sex = "null";
}
}
}
package com.zzh.oop.demo1;
public class LittleStudent extends Student {
public LittleStudent(){
// 隐藏代码:调用父类无参构造。
super();//必须放置在构造函数第一行
System.out.println("我是小学生");
}
public void print(){
System.out.println("子类");
}
public void test(){
print();
super.print();
this.print();
}
}
package com.zzh.oop.demo1;
public class Application {
public static void main(String[] args) {
LittleStudent student = new LittleStudent();
student.test();
student.setName("Tom");
student.setSex("男");
System.out.println(student.getName()+":"+student.getSex());
}
}
supper vs this:
supper:
- 1.super调用父类的构造方法,必须在构造方法的第一个。
- 2.super必须只能出现在子类的方法和构造方法中。
- 3.super和this不能同时调用构造方法。
vs this:
- 代表的对象不同:
this :本类调用者这个对象。
super:代表父类对象的引用。 - 前提:
this:没有继承也可以使用。
super:只能在继承条件才可以使用。 - 构造方法:
this():本类的构造方法。
super():父类的构造。
重写:需要有继承关系,子类重写父类的方法!
重写方法必须一致,但方法体可以不同
子类重写父类方法,执行子类的方法
1.方法名必须相同
2.参数列表必须相同
3.修饰符:范围可以扩大:public > Protected > Default > private
4.抛出异常:范围可以被缩小,但不能扩大
例:
package com.zzh.oop.demo1;
public class LittleStudent extends Student {
public LittleStudent(){
// 隐藏代码:调用父类无参构造。
super();//必须放置在构造函数第一行
System.out.println("我是小学生");
}
@Override
public void print() {
super.print();
}
}
package com.zzh.oop.demo1;
public class Student {
//属性名私有
private String name;
private int id;
private String sex;
//提供一些public的get,set方法
// Alt + Insert
public Student() {
System.out.println("我是学生");
}
public void print(){
System.out.println("父类");
}
}
package com.zzh.oop.demo1;
public class Application {
//静态方法和非静态方法有区别
//静态方法:方法的调用只和左边,定义的数据类型有关
//非静态:才能重写
public static void main(String[] args) {
LittleStudent littleStudent = new LittleStudent();
// Alt + Enter, Enter
littleStudent.print();
Student student1 = new LittleStudent();
student1.print();
}
}
多态
子类重写父类方法,执行子类的方法
-
多态存在的条件
有继承关系
子类重写父类方法
父类引用指向子类 -
多态中成员的特点
1.多态成员变量:编译运行看左边
Fu f=new Zi();
System.out.println(f.num);//f是Fu中的值,只能取到父中的值
2.多态成员方法:编译看左边,运行看右边
Fu f1=new Zi();
System.out.println(f1.show());//f1的门面类型是Fu,但实际类型是Zi,所以调用的是重写后的方法。
原文链接:https://blog.csdn.net/qq_41679818/article/details/90523285
例:
package com.zzh.oop.demo1;
public class LittleStudent extends Student {
@Override
public void print() {
System.out.println("子类");
}
}
package com.zzh.oop.demo1;
public class Student {
public Student() {
System.out.println("我是学生");
}
public void print(){
System.out.println("父类");
}
}
package com.zzh.oop.demo1;
public class Application {
//静态方法和非静态方法有区别
//静态方法:方法的调用只和左边,定义的数据类型有关
//非静态:才能重写
public static void main(String[] args) {
LittleStudent littleStudent = new LittleStudent();
Student student = new LittleStudent();
Object student1 = new LittleStudent();
student1.print();
// 相当于((LittleStudent) student1).print();
}
}
instanceof
判断对象和类有无父子关系,返回ture or false
Object student1 = new LittleStudent();
System.out.println(student1 instanceof Student) //True
类型转换
(类名)对象
低转高不用强制转换
Student student = new LittleStudent();
// 高 低
高转低需要强制转换
Student student = new LittleStudent();
(LittleStudent) student;
static 关键字
- 静态代码块
public class Demo3 {
{
// 匿名代码块 2 赋初始值
System.out.println("匿名代码块");
}
static {
// 静态代码块 1 只执行一次
System.out.println("静态代码块");
}
public Demo3(){
//构造方法 3
System.out.println("构造方法");
}
public static void main(String[] args) {
Demo3 demo3 = new Demo3();
Demo3 demo1 = new Demo3();
/* 输出结果
静态代码块
匿名代码块
构造方法
匿名代码块
构造方法
* */
}
}
- 静态导入包
/ 静态导入包
import static java.lang.Math.random;
import static java.lang.Math.PI;
public class Demo4 {
public static void main(String[] args) {
System.out.println(random());
System.out.println(PI);
}
}
抽象类
- 不能new这个抽象类,只能靠子类去实现
- 抽象类可以写普通方法
- 抽象方法必须写在抽象类中
public class Application {
public static void main(String[] args) {
// Student student = new Student(); 抽象类不能new 'Student' is abstract; cannot be instantiated
Student student = new LittleStudent();
student.lenrn();
}
}
//abstract 抽象方类
public abstract class Student {
//abstract 抽象方法,只有方法名字,没有方法的实现
public abstract void lenrn();
}
public class LittleStudent extends Student{
@Override
public void lenrn() {
System.out.println("English");
}
}
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· 【自荐】一款简洁、开源的在线白板工具 Drawnix
· 没有Manus邀请码?试试免邀请码的MGX或者开源的OpenManus吧
· 园子的第一款AI主题卫衣上架——"HELLO! HOW CAN I ASSIST YOU TODAY
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本