系列文章目录
Java面试题·解释题·JavaSE部分
Java面试题·解释题·框架部分
Java面试题·解释题·单例模式、工厂模式、代理模式部分
文章目录
- 系列文章目录
- 前言
- 一、设计模式
-
- [1. 单例模式](#1. 单例模式)
-
- [1.1 单例模式的定义](#1.1 单例模式的定义)
- [1.2 单例模式的实现方法](#1.2 单例模式的实现方法)
- [2. 工厂模式](#2. 工厂模式)
-
- [2.1 工厂模式的定义](#2.1 工厂模式的定义)
- [2.2 工厂模式的实现方法](#2.2 工厂模式的实现方法)
- [2.3 工厂模式的好处](#2.3 工厂模式的好处)
- [2.4 工厂模式的使用场景](#2.4 工厂模式的使用场景)
- [3. 代理模式](#3. 代理模式)
-
- [3.1 代理模式的定义](#3.1 代理模式的定义)
- [3.2 代理模式的实现方法](#3.2 代理模式的实现方法)
- [3.3 代理模式的好处](#3.3 代理模式的好处)
- [3.4 动态代理以及静态代理的区别](#3.4 动态代理以及静态代理的区别)
-
- [3.4.1 静态代理](#3.4.1 静态代理)
- [3.4.2 动态代理](#3.4.2 动态代理)
- [3.4.3 动态代理和静态代理的区别](#3.4.3 动态代理和静态代理的区别)
- 总结
前言
本文将介绍:
单例模式、
工厂模式、
代理模式
本文主要介绍以上部分的面试题。
一、设计模式
设计模式是为了专门解决特定问题的模板,如果需求符合问题,设计模式能更简单、更正确的解决问题。
1. 单例模式
1.1 单例模式的定义
单例模式:该类能且仅能出现一个对象;该类必须自行创建该对象;该类必须将对象提供给外部。
该类只能有一个实例 :此类只提供私有的构造函数;
该类必须自行创建该对象 :此类定义中有一个私有静态的对象;
该类必须将对象提供给外部 :此类定义中有静态公有方法能够创建并获取到静态私有对象并返回;
创建的方法和获取的方法可以是同一个方法
1.2 单例模式的实现方法
饿汉式:饿汉式是在类加载时就进行初始化。它的实现方法是在类加载的时候就创建并初始化。饿汉式的特点是线程安全,但可能会造成资源浪费。
懒汉式:懒汉式是在首次使用时进行初始化。懒汉式的实现方法是在需要时进行延迟初始化。懒汉式的特点是线程不安全,需要考虑多线程环境下的同步问题。
2. 工厂模式
2.1 工厂模式的定义
工厂模式:用于封装对象的创建过程,将对象的实例化过程与使用过程分离。
定义一个工厂类,该类负责根据客户端的需求创建具体的对象,并将对象返回给客户端使用。客户端通过调用工厂类的方法来获取对象,而无需直接依赖于具体的对象实现类。
2.2 工厂模式的实现方法
抽象产品 (Abstract Product):定义产品的共同接口,可以是抽象类或接口。
具体产品 (Concrete Product):实现抽象产品接口,是工厂所创建的对象。
工厂类 (Factory Class):负责创建具体产品对象的类。根据客户端传入的参数决定创建哪种对象。
简单工厂模式的优点包括:
2.3 工厂模式的好处
封装对象的创建过程,客户端只需要关心产品的接口,无需关心具体的实现类。
可以通过工厂类来集中管理和控制对象的创建,提供更高的灵活性和可维护性。
可以通过工厂类来隐藏具体产品的实现细节,对客户端代码进行解耦,提供更好的扩展性。
简单工厂模式的缺点是当需要添加新的产品时,需要修改工厂类的代码,违反了开闭原则。同时,工厂类集中了所有产品的创建逻辑,可能导致工厂类的代码变得庞大而复杂。
2.4 工厂模式的使用场景
需要创建一组相关对象的场景,这些对象共享相同的接口或基类。
需要隐藏对象创建的具体细节,只暴露产品的接口给客户端。
需要根据不同的条件创建不同的对象。
3. 代理模式
3.1 代理模式的定义
代理模式的核心思想是通过一个代理对象来间接访问目标对象,代理对象和目标对象实现了相同的接口或继承了相同的父类,以便代理对象可以完全替代目标对象。
3.2 代理模式的实现方法
抽象对象接口 (Subject):定义了目标对象和代理对象的共同接口,可以是抽象类或接口。
目标对象 (Real Subject):定义了代理对象所代表的真实对象,是客户端真正要访问的对象。
代理对象(Proxy):持有目标对象的引用,并在访问目标对象之前或之后进行一些额外的操作。
3.3 代理模式的好处
代理模式可以在不改变目标对象的前提下,通过引入代理对象来对目标对象进行扩展或增强。
代理模式可以实现客户端和目标对象之间的解耦,客户端只需要通过代理对象来访问目标对象,无需关心具体的实现细节。
代理模式可以在访问目标对象之前或之后添加一些额外的操作,如权限控制、缓存、日志记录等。(AOP)
3.4 动态代理以及静态代理的区别
动态代理和静态代理都是代理模式的具体实现方式,用于控制对目标对象的访问。它们的主要区别在于代理类的生成方式和访问方式。
3.4.1 静态代理
静态代理是在编译时创建代理类,在编码阶段就已经确定了代理对象和目标对象的关系。在静态代理中,需要手动编写代理类,代理类和目标类都实现了同一个接口或继承了同一个父类。代理类持有目标对象的引用,并在方法调用前后进行一些额外的操作。静态代理的优点是简单直接,易于理解和实现。但是,静态代理的缺点是在代理类和目标类之间存在强耦合,如果需要代理多个类,就需要编写多个代理类。
3.4.2 动态代理
动态代理是在运行时动态生成代理类,无需手动编写代理类。动态代理利用Java的反射机制,在运行时动态地创建代理类和代理对象。在动态代理中,代理对象通过实现InvocationHandler接口来定义代理类的行为。当调用代理对象的方法时,会被重定向到InvocationHandler的invoke方法,并在该方法中执行一些额外的操作。动态代理的优点是可以代理多个类,通过同一个代理类来完成对不同目标对象的访问。但是,动态代理的缺点是相对于静态代理来说,实现更加复杂。
3.4.3 动态代理和静态代理的区别
代理类的生成方式 :静态代理在编译时创建代理类,需要手动编写代理类;而动态代理是在运行时动态生成代理类,无需手动编写代理类。
对象的访问方式 :静态代理的访问方式在编译时确定,代理对象对目标对象的访问是静态的;而动态代理的访问方式在运行时确定,代理对象对目标对象的访问是动态的。
扩展性:静态代理需要为每个目标对象编写一个代理类,扩展性较差;而动态代理可以适用于多个目标对象,通过同一个代理类来完成对不同目标对象的访问,扩展性较好。
总结
以上是单例模式、工厂模式、代理模式部分的解释题,感谢各位客官收看。