Java学习_面向对象编程
- 抽象类
- 一个
class定义了方法,但没有具体执行代码,这个方法就是抽象方法,抽象方法用abstract修饰。因为抽象类本身被设计成只能用于被继承,因此,抽象类可以强迫子类实现其定义的抽象方法,否则编译会报错。因此,抽象方法实际上相当于定义了“规范”。 - 抽象方法的类都是抽象类,抽象类不全是抽象方法。
面向抽象编程的本质就是:
上层代码只定义规范(例如:
abstract class Person);不需要子类就可以实现业务逻辑(正常编译);
具体的业务逻辑由不同的子类实现,调用者并不关心。
- 一个
- 接口
- 如果一个抽象类没有字段,且所有方法全部都是抽象方法,就可以把该抽象类改写为接口:
interface。 - 接口中属性默认public static final 修饰 方法默认public abstract修饰
- 一个具体的
class去实现一个interface时,需要使用implements关键字。 - 一个类可以实现多个
interface。 - 一个
interface可以继承自另一个interface。interface继承自interface使用extends,它相当于扩展了接口的方法。
1 interface Hello {
2 void hello();
3 }
4
5 interface Person extends Hello {
6 void run();
7 String getName();
8 }
- 如果一个抽象类没有字段,且所有方法全部都是抽象方法,就可以把该抽象类改写为接口:
- 包
- 在Java虚拟机执行的时候,JVM只看完整类名,因此,只要包名不同,类就不同。
- 包没有父子关系。java.util和java.util.zip是不同的包,两者没有任何继承关系。
- 位于同一个包的类,可以访问包作用域的字段和方法。不用
public、protected、private修饰的字段和方法就是包作用域。 import
- 直接写出完整类名 mr.jun.Arrays arrays = new mr.jun.Arrays();
- 用
import语句,导入Arrays,然后写简单类名。1 // Person.java
2 package ming;
3
4 // 导入完整类名:
5 import mr.jun.Arrays;
6
7 public class Person {
8 public void run() {
9 Arrays arrays = new Arrays();
10 }
11 } import static 包名,它可以导入一个类的静态字段和静态方法。1 package main;
2
3 // 导入System类的所有静态字段和静态方法:
4 import static java.lang.System.*;
5
6 public class Main {
7 public static void main(String[] args) {
8 // 相当于调用System.out.println(…)
9 out.println("Hello, world!");
10 }
11 }如果是简单类名,按下面的顺序依次查找:
查找当前
package是否存在这个class;查找
import的包是否包含这个class;查找
java.lang包是否包含这个class。
- 因此,编写class的时候,编译器会自动帮我们做两个import动作:
默认自动
import当前package的其他class;默认自动
import java.lang.*。- 自动导入的是java.lang包,但类似java.lang.reflect这些包仍需要手动导入。
- 如果有两个
class名称相同,例如,mr.jun.Arrays和java.util.Arrays,那么只能import其中一个,另一个必须写完整类名。
- 内部类
- 普通类有个最大的不同,就是Inner Class的实例不能单独存在,必须依附于一个Outer Class的实例。
1 public class Main {
2 public static void main(String[] args) {
3 Outer outer = new Outer("Nested"); // 实例化一个Outer
4 Outer.Inner inner = outer.new Inner(); // 实例化一个Inner
5 inner.hello();
6 }
7 }
8
9 class Outer {
10 private String name;
11
12 Outer(String name) {
13 this.name = name;
14 }
15
16 class Inner {
17 void hello() {
18 System.out.println("Hello, " + Outer.this.name);
19 }
20 }
21 } - Inner Class和普通Class相比,除了能引用Outer实例外,还有一个额外的“特权”,就是可以修改Outer Class的
private字段,因为Inner Class的作用域在Outer Class内部,所以能访问Outer Class的private字段和方法。(Inner Class除了有一个this指向它自己,还隐含地持有一个Outer Class实例,可以用Outer.this访问这个实例。) - 匿名内部类
- 不需要在Outer Class中明确地定义这个Class,而是在方法内部,通过匿名类(Anonymous Class)来定义。
1 public class Main {
2 public static void main(String[] args) {
3 Outer outer = new Outer("Nested");
4 outer.asyncHello();
5 }
6 }
7
8 class Outer {
9 private String name;
10
11 Outer(String name) {
12 this.name = name;
13 }
14
15 void asyncHello() {
16 Runnable r = new Runnable() { //重写父类或者接口的方法
17 @Override
18 public void run() {
19 System.out.println("Hello, " + Outer.this.name);
20 }
21 };
22 new Thread(r).start();
23 }
24 }
- 不需要在Outer Class中明确地定义这个Class,而是在方法内部,通过匿名类(Anonymous Class)来定义。
- 静态内部类
1 public class Main {
2 public static void main(String[] args) {
3 Outer.StaticNested sn = new Outer.StaticNested(); //外部类无需实例化
4 sn.hello();
5 }
6 }
7
8 class Outer {
9 private static String NAME = "OUTER";
10
11 private String name;
12
13 Outer(String name) {
14 this.name = name;
15 }
16
17 static class StaticNested {
18 void hello() {
19 System.out.println("Hello, " + Outer.NAME);
20 }
21 }
22 }- 用
static修饰的内部类和Inner Class有很大的不同,它不再依附于Outer的实例,而是一个完全独立的类,因此无法引用Outer.this,但它可以访问Outer的private静态字段和静态方法。如果把StaticNested移到Outer之外,就失去了访问private的权限。
- 普通类有个最大的不同,就是Inner Class的实例不能单独存在,必须依附于一个Outer Class的实例。
classpath和jar
classpath和jar- 图1

- 图2

- 图1
- 模块
- 多态
- 在继承关系中,子类如果定义了一个与父类方法签名完全相同的方法,被称为覆写(Override)。
- Java的实例方法调用是基于运行时的实际类型的动态调用,而非变量的声明类型。(多态)
public void runTwice(Person p) {
p.run();
p.run();
}它传入的参数类型是
Person,我们是无法知道传入的参数实际类型究竟是Person,还是Student,还是Person的其他子类,因此,也无法确定调用的是不是Person类定义的run()方法。
覆写Object方法
toString():把instance输出为String;equals():判断两个instance是否逻辑相等;Java equals方法学习hashCode():计算一个instance的哈希值。
- 在子类的覆写方法中,如果要调用父类的被覆写的方法,可以通过
super来调用。class Person {
protected String name;
public String hello() {
return "Hello, " + name;
}
} Student extends Person {
@Override
public String hello() {
// 调用父类的hello()方法:
return super.hello() + "!";
}
} - 方法标记为
final。用final修饰的方法不能被Override: - 类本身标记为
final。用final修饰的类不能被继承: - 用
final修饰的字段(包括局部变量)在初始化后不能被修改。- 可以在构造方法中初始化final字段123
1 class Person {
2 public final String name;
3 public Person(String name) {
4 this.name = name;
5 }
6 }
- 可以在构造方法中初始化final字段123
- 抽象类
- 一个
class定义了方法,但没有具体执行代码,这个方法就是抽象方法,抽象方法用abstract修饰。因为抽象类本身被设计成只能用于被继承,因此,抽象类可以强迫子类实现其定义的抽象方法,否则编译会报错。因此,抽象方法实际上相当于定义了“规范”。 - 抽象方法的类都是抽象类,抽象类不全是抽象方法。
面向抽象编程的本质就是:
上层代码只定义规范(例如:
abstract class Person);不需要子类就可以实现业务逻辑(正常编译);
具体的业务逻辑由不同的子类实现,调用者并不关心。
- 一个
- 接口
- 如果一个抽象类没有字段,且所有方法全部都是抽象方法,就可以把该抽象类改写为接口:
interface。 - 接口中属性默认public static final 修饰 方法默认public abstract修饰
- 一个具体的
class去实现一个interface时,需要使用implements关键字。 - 一个类可以实现多个
interface。 - 一个
interface可以继承自另一个interface。interface继承自interface使用extends,它相当于扩展了接口的方法。
- 如果一个抽象类没有字段,且所有方法全部都是抽象方法,就可以把该抽象类改写为接口:
- 包
- 在Java虚拟机执行的时候,JVM只看完整类名,因此,只要包名不同,类就不同。
- 包没有父子关系。java.util和java.util.zip是不同的包,两者没有任何继承关系。
- 位于同一个包的类,可以访问包作用域的字段和方法。不用
public、protected、private修饰的字段和方法就是包作用域。 import
- 直接写出完整类名 mr.jun.Arrays arrays = new mr.jun.Arrays();
- 用
import语句,导入Arrays,然后写简单类名。1 // Person.java
2 package ming;
3
4 // 导入完整类名:
5 import mr.jun.Arrays;
6
7 public class Person {
8 public void run() {
9 Arrays arrays = new Arrays();
10 }
11 } import static 包名,它可以导入一个类的静态字段和静态方法。1 package main;
2
3 // 导入System类的所有静态字段和静态方法:
4 import static java.lang.System.*;
5
6 public class Main {
7 public static void main(String[] args) {
8 // 相当于调用System.out.println(…)
9 out.println("Hello, world!");
10 }
11 }如果是简单类名,按下面的顺序依次查找:
查找当前
package是否存在这个class;查找
import的包是否包含这个class;查找
java.lang包是否包含这个class。
- 因此,编写class的时候,编译器会自动帮我们做两个import动作:
默认自动
import当前package的其他class;默认自动
import java.lang.*。- 自动导入的是java.lang包,但类似java.lang.reflect这些包仍需要手动导入。
- 如果有两个
class名称相同,例如,mr.jun.Arrays和java.util.Arrays,那么只能import其中一个,另一个必须写完整类名。
内部类
- 普通类有个最大的不同,就是Inner Class的实例不能单独存在,必须依附于一个Outer Class的实例。
1 public class Main {
2 public static void main(String[] args) {
3 Outer outer = new Outer("Nested"); // 实例化一个Outer
4 Outer.Inner inner = outer.new Inner(); // 实例化一个Inner
5 inner.hello();
6 }
7 }
8
9 class Outer {
10 private String name;
11
12 Outer(String name) {
13 this.name = name;
14 }
15
16 class Inner {
17 void hello() {
18 System.out.println("Hello, " + Outer.this.name);
19 }
20 }
21 } - Inner Class和普通Class相比,除了能引用Outer实例外,还有一个额外的“特权”,就是可以修改Outer Class的
private字段,因为Inner Class的作用域在Outer Class内部,所以能访问Outer Class的private字段和方法。(Inner Class除了有一个this指向它自己,还隐含地持有一个Outer Class实例,可以用Outer.this访问这个实例。) - 匿名内部类
- 不需要在Outer Class中明确地定义这个Class,而是在方法内部,通过匿名类(Anonymous Class)来定义。
1 public class Main {
2 public static void main(String[] args) {
3 Outer outer = new Outer("Nested");
4 outer.asyncHello();
5 }
6 }
7
8 class Outer {
9 private String name;
10
11 Outer(String name) {
12 this.name = name;
13 }
14
15 void asyncHello() {
16 Runnable r = new Runnable() { //重写父类或者接口的方法
17 @Override
18 public void run() {
19 System.out.println("Hello, " + Outer.this.name);
20 }
21 };
22 new Thread(r).start();
23 }
24 }
- 不需要在Outer Class中明确地定义这个Class,而是在方法内部,通过匿名类(Anonymous Class)来定义。
- 静态内部类
1 public class Main {
2 public static void main(String[] args) {
3 Outer.StaticNested sn = new Outer.StaticNested(); //外部类无需实例化
4 sn.hello();
5 }
6 }
7
8 class Outer {
9 private static String NAME = "OUTER";
10
11 private String name;
12
13 Outer(String name) {
14 this.name = name;
15 }
16
17 static class StaticNested {
18 void hello() {
19 System.out.println("Hello, " + Outer.NAME);
20 }
21 }
22 }- 用
static修饰的内部类和Inner Class有很大的不同,它不再依附于Outer的实例,而是一个完全独立的类,因此无法引用Outer.this,但它可以访问Outer的private静态字段和静态方法。如果把StaticNested移到Outer之外,就失去了访问private的权限。
- 普通类有个最大的不同,就是Inner Class的实例不能单独存在,必须依附于一个Outer Class的实例。
classpath和jar
classpath和jar
- 图1

- 图2

- 图1
- 模块
Java学习_面向对象编程的更多相关文章
- Java学习之==>面向对象编程 Part2
一.封装 封装,即隐藏对象的属性和实现细节,仅对外公开接口,控制在程序中属性的读和修改的访问级别:将抽象得到的数据和行为(或功能)相结合,形成一个有机的整体,也就是将数据与操作数据的源代码进行有机的结 ...
- JAVA学习:面向对象编程
"算法+数据结构=程序"是一句经典名言,这句话很直接的说明了程序的本质:处理数据.产生结果.即便是最简单的HelloWorld程序,我们也可以将字符串"HelloWorl ...
- Java学习day7面向对象编程1-对象和类
一.Java编程中对象和类的概念 1,什么是类? 答:类是客观存在的,抽象的,概念的东西. 2,什么是对象? 答:对象是具体的,实际的,代表一个事物.例如:车是一个类,汽车,自行车就是他的对象. 关于 ...
- Java学习之==>面向对象编程 Part1
一.面向对象与面向过程 1.面向过程 角度是功能,以方法为最小单位,思考的是具体怎么做. 2.面向对象 角度是抽象,以类为最小单位,思考的是谁来做. 3.示例:“小明去上班” 面向过程 起床,刷牙洗脸 ...
- Java学习day9面向对象编程2-方法的可变个数的参数和方法的参数传递
一.方法的可变个数的参数. 问题:我们能够打印的信息都是来源于方法的参数,也就是形参的传递.那如何要给方法传递不同的参数? .1.采用数组形参来定义方法 public static void test ...
- Java学习day8面向对象编程2-类的属性和方法
一.类的属性 1.语法格式 修饰符 类型 属性名 = 初值 说明:修饰符private:该属性只能由该类的方法使用.在同一类内可见.使用对象:变量.方法. 注意:不能修饰类(外部类) 修饰符pu ...
- 0028 Java学习笔记-面向对象-Lambda表达式
匿名内部类与Lambda表达式示例 下面代码来源于:0027 Java学习笔记-面向对象-(非静态.静态.局部.匿名)内部类 package testpack; public class Test1{ ...
- Java基础-初识面向对象编程(Object-Oriented-Programming)
Java基础-初识面向对象编程(Object-Oriented-Programming) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. Java是一门面向对象的程序设计语言.那么什 ...
- 0030 Java学习笔记-面向对象-垃圾回收、(强、软、弱、虚)引用
垃圾回收特点 垃圾:程序运行过程中,会为对象.数组等分配内存,运行过程中或结束后,这些对象可能就没用了,没有变量再指向它们,这时候,它们就成了垃圾,等着垃圾回收程序的回收再利用 Java的垃圾回收机制 ...
随机推荐
- 题解 洛谷 P2612 【[ZJOI2012]波浪】DP+高精
题目描述 题目传送门 分析 因为有绝对值不好处理,所以我们强制从小到大填数 设 \(f[i][j][p][o]\) 为当前填到了第 \(i\) 个数,波动强度为 \(j\),有 \(p\) 个连续段并 ...
- SpringCloud 源码系列(1)—— 注册中心 Eureka(上)
Eureka 是 Netflix 公司开源的一个服务注册与发现的组件,和其他 Netflix 公司的服务组件(例如负载均衡.熔断器.网关等)一起,被 Spring Cloud 整合为 Spring C ...
- 第8.6节 Python类中的__new__方法深入剖析:调用父类__new__方法参数的困惑
上节<第8.5节 Python类中的__new__方法和构造方法__init__关系深入剖析:执行顺序及参数关系案例详解>通过案例详细分析了两个方法的执行顺序,不知大家是否注意到了,在上述 ...
- 常见SQL注入点判断
sql注入手工检测 SQL注入手工检测 1基本检测 数字型 字符型 搜索型 POST注入 布尔盲注 报错注入 堆叠注入 判断是什么数据库 2绕过技巧 大小写 替换关键字 使用编码 注释和符号 等价函数 ...
- swpuCTF2019 web1 无列名注入
上周参加的swpuctf比赛第一道web题做了好久,在最后一个小时用非预期的方法做出来了,看了官方题解之后记录一下wp里面的无列名注入. 关于无列名注入可以看一下这篇链接 https://www.ch ...
- 颜色直方图(Color Histogram)
数字成像中的颜色直方图是对给定图像中具有相同颜色的像素的频率进行计算的一种方法.这种方法通常被转换成一个图形,以帮助分析和调整图像中的平衡.几乎所有的照片编辑软件和大量的数码相机都具有颜色直方图的查看 ...
- P6100 [USACO19FEB]Painting the Barn G
本题解提供的做法思路应该是比较清晰的,可惜代码实现比较繁琐,仅供大家参考. 题解 不难发现 \(x\) ,\(y\) 的取值范围只有 \(200\) ,所以我们可以考虑从这里入手.我们可以先通过二维前 ...
- 【SPOJ QTREE4】Query on a tree IV(树链剖分)
Description 给出一棵边带权(\(c\))的节点数量为 \(n\) 的树,初始树上所有节点都是白色.有两种操作: C x,改变节点 \(x\) 的颜色,即白变黑,黑变白. A,询问树中最远的 ...
- nginx: [emerg] bind() to 0.0.0.0:80 failed (48: Address already in use)
Mac上启动nginx报如上错误,原因是80端口已被占用,可能有些服务未能成功关闭. 解决:键入命令 sudo nginx -s stop ( 或 sudo nginx -s quit) ,然后 s ...
- 解压版mysql+免破解版Navicat,好用!
解压版mysql安装流程 获取mysql压缩包 获取地址: 链接:https://pan.baidu.com/s/1HqdFDQn_6ccPM0gOftApIg 提取码:n19t 获取压缩包后可安装压 ...