一.单例设计模式(是一种思想)
核心思想:在程序的运行当中 该类的对象 不管怎么创建 始终保持有且只有一个该类的对象
编写单例类思路:
1.不让外界创建对象(私有化构造方法)
2.自己类内部 来创建这个对象(让这个对象只创建一次)
3.给类外部 提供一个获取该对象的方法(相当于提供一个get方法)
1️⃣.饿汉式
只要该类被加载 就会在方法区的静态区中创建本类对象
example:
class SingleHungry{
//声明一个本类的对象
private static SingleHungry singleHungry = new SingleHungry();
//构造方法私有化
private SingleHungry() {
}
//对外提供一个访问的方法(就是为了返回本类的对象)
public static SingleHungry getInstance() {
return singleHungry;
}
}
2️⃣.懒汉式(延迟加载)
在类被加载的时候 不会去创建对象
只有当你调用了获取该类对象的方法的时候 才会创建该类的对象
(不完整 线程安全问题 双锁控制可以解决)
example:
class SingleLazy{
//声明一个对象的引用
private static SingleLazy singleLazy = null;
private SingleLazy() {
}
//获取对象的方法
public static SingleLazy getInstance() {
//判断 当这个对象不存在的时候再创建
if (singleLazy == null) {
singleLazy = new SingleLazy();
}
return singleLazy;
}
}
二.抽象类
关键词:abstract
abstract可以修饰类 该类即为抽象类
abstract可以修饰方法 该方法就是抽象方法
当你对这个方法描述的不是很清楚(不知道该怎么写清楚的时候)就可以直接把该方法 声明成抽象方法
注意:抽象方法 没有方法的实现部分
注意:
1.有抽象方法的类 必须是抽象类
2.但是抽象类中不一定要有抽象方法
3.抽象类不能直接创建对象
4.强制子类重写父类的抽象方法
5.使用多态的形式 进行创建
抽象类的作用:
核心:抽象类不能直接使用 只能使用抽象类的子类
抽象类中有什么:
1.可以有变量 常量
2.可以有构造方法
3.可以有抽象方法和成员方法
example:
public class Demo{
public static void main(String[] args) {
//创建一个动物对象
// Animal animal = new Animal() {};(会报错!)
//抽象类如何使用
//需要使用多态的创建方式
//父类引用指向子类对象
Animal animal = new LiNaiAng();
animal.speak();
}
}
abstract class Animal{
//构造方法
public Animal() {
System.out.println("我是Animal无参的构造方法");
}
//声明一个抽象方法
public abstract void speak();
public void fun() {
System.out.println("我是fun方法");
}
}
//抽象类的子类
class LiNaiAng extends Animal{
//子类重写父类的抽象方法
@Override
public void speak() {
System.out.println("汪汪汪");
}
}
tips:
1.abstract关键词与哪些关键词不能共存?
2.final 不可以:修饰抽象方法 方法不能被重写
3.private 不可以:private修饰方法 只能本类访问
抽象类 强制子类去重写抽象方法 访问不到就谈不上重写了
4.static 修饰抽象方法 可以用类名去调用
抽象方法是没有实现部分的 不能直接调用
三.模(mú)板设计模式
example:
abstract class LOStudy{
//学习方法
public void study() {
System.out.println("报名");
//选择学科是需要变化的 声明一个方法
//调用抽象方法
chooseSubject();
System.out.println("找工作");
}
//声明抽象方法
public abstract void chooseSubject();
}
class LNA extends LOStudy{
//重写方法
@Override
public void chooseSubject() {
System.out.println("学Unity3D");
}
}
class LYC extends LOStudy{
//重写方法
@Override
public void chooseSubject() {
System.out.println("学java");
}
}
example:
计算某一段程序的执行时间
public class Demo02 {
public static void main(String[] args) {
//获取系统时间
//当前时间距离1970年的1月1日 的时间 单位是毫秒
Time time = new Test();
time.fun();
}
}
abstract class Time{
public void fun() {
long start = System.currentTimeMillis();
//执行某一个程序
program();
long stop = System.currentTimeMillis();
System.out.println("该程序耗时" + (stop - start) + "毫秒");
}
public abstract void program();
}
class Test extends Time{
@Override
public void program() {
for (int i = 0; i < 1000; i++) {
for (int j = 0; j < 1000; j++) {
System.out.println(i + j);
}
}
}
}
四.接口
狭义:
java中的接口
使用interface关键词来声明
写法:interface 接口名{ }
广义:
相当于一个规则 规范 是需要来遵守的
接口:final 默认是静态的常量
1.只可以声明抽象方法(是不准确的)
2.声明变量
3.接口只能用来实现(不能继承)
4.接口中是没有构造方法的(使用的是实现这个关键词 不是继承)
5.接口中声明的变量 默认是public static
6.声明抽象方法的时候 默认是 public abstract修饰(可省略)
接口是怎么运行的?
和类一样 也会被翻译成.class文件被执行
接口使用 implements 关键词实现
接口的实现类 类名一般都以Impl结尾
public class Demo03 {
public static void main(String[] args) {
//创建接口 使用多态的形式创建
InterA a = new InterAImpl();
a.fun();
}
}
//声明一个接口
interface InterA{
int num = 10;
public void fun();
}
class InterAImpl implements InterA{
//实现接口中的抽象方法
@Override
public void fun() {
//num = 15;
System.out.println(num);
System.out.println("我是实现类的fun方法");
}
}
接口中是没有构造方法的
抽象类 和 接口有什么区别?
1.使用方法
抽象类:继承 extends
接口:实现 implements
2.成员变量
抽象类:可以是常量也可以是变量
接口:只能是常量
3.成员方法
抽象类:可以是抽象方法 也可以是成员方法
接口:只能是抽象方法(静态方法 和 默认方法)
4.构造方法
抽象类:有
接口:没有
1.类与类之间的关系(亲Dad的关系)
只允许单继承
2.类和接口的关系(干Dad的关系)
实现的关系 可以实现多个接口
3.接口和接口的关系
可以单继承 也可以 多继承
//类和接口的关系
interface InterB{
public abstract void fun1();
}
interface InterC{
public abstract void fun2();
}
class TestA implements InterB,InterC{
@Override
public void fun2() {
// TODO Auto-generated method stub
}
@Override
public void fun1() {
// TODO Auto-generated method stub
}
}
//接口和接口的关系
interface InterD{
public abstract void fun1();
}
interface InterE{
public abstract void fun2();
}
interface InterF extends InterD,InterE{
}
class InterFImpl implements InterF{
@Override
public void fun1() {
}
@Override
public void fun2() {
}
}
JDK1.8后的新特性
接口中扩充了静态方法 和 默认方法
public class Demo06 {
public static void main(String[] args) {
//调用接口中的 静态方法
InterX.staticFun();
//创建实现类的对象(多态方式)
InterX x = new InterXImpl();
x.defaultFun();
//实现类中的静态方法
InterXImpl.staticFun();
//调用实现类的特有方法
InterXImpl xImpl = (InterXImpl)x;
xImpl.print();
}
}
interface InterX{
//抽象方法
public abstract void fun();
//静态方法
public static void staticFun() {
System.out.println("我是接口中的staticFun方法");
}
//默认方法 default 关键词
//不是必须在实现类中重写
public default void defaultFun() {
System.out.println("我是接口中的defaultFun");
}
}
class InterXImpl implements InterX{
//实现接口中的抽象方法
@Override
public void fun() {
System.out.println("我是实现类中的fun方法");
}
//重写默认方法
@Override
public void defaultFun() {
//调用父类中的 默认方法
//接口名.super.默认方法名
InterX.super.defaultFun();
System.out.println("我是实现类中的defaultFun方法");
}
//静态不重写 实现类自己的静态方法
public static void staticFun() {
System.out.println("我是实现类中的staticFun方法");
}
//自己的方法(能不能调用 父类默认方法)
public void print() {
InterX.super.defaultFun();
System.out.println("我是打印方法");
}
}