栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

尚硅谷—韩顺平—图解 Java设计模式

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

尚硅谷—韩顺平—图解 Java设计模式

​视频链接

一.:设计模式面试题 & 课程介绍(1~4) 1.:原型设计模式的,几个经典面试题:

   1)请使用 UML 类图,画出原型模式核心角色?
   2)原型设计模式的深拷贝 & 浅拷贝是什么?
     并写出 深拷贝的,两种方式的源码?

    -1:重写 clone 方法,实现深拷贝。
    -2:使用序列化方式,实现深拷贝。
   3)在 Spring 框架中,哪里使用到原型模式,并对原吗进行分析:

   4)Spring 中,原型 Bean 的创建,就是原型模式的应用:
   5)代码分析 + Bebug源码:(要求比较高)

   6)设计模式的七大原则:要求:
    -1:七大设计原则核心思想。
    -2:能够以 UML 类图,说明设计原则。
    -3:在项目实际开发中,你在哪里使用到了 ocp 原则。(开闭原则)
    -4:设计模式,常用的 七大原则有:
      -1:单一职责原则
      -2:接口隔离原则
      -3:依赖倒转原则
      -4:里氏替换原则
      -5:开闭原则
      -6:迪米特法则
      -7:合成复用原则(可无)

   7)金融借贷平台项目:状态模式进行设计

   8)解释器设计模式:


   9)单例设计模式:


2.:何时会用到设计模式 & 重要性

   1)设计模式的重要性:
    -1:软件工程中:设计模式(design pattern),是对 软件设计中普遍存在(反复出现) 的各种问题,所提出的解决方案。
    -2:这个术语:是由 埃里希伽马 等人,在 1990 年代,从建筑设计领域,引入到计算机科学的。
    -3:当一个项目开发完成后,如果客户提出新增功能,怎么办。
    -4:目前:一线大厂,都会问你,在实际项目中,使用过什么设计模式,怎么样使用,解决了什么问题?
    -5:设计模式,在软件中哪里存在?
=> 面向对象(oo)
=> 功能模块【设计模式 + 算法(使用数据结构)】
=> 框架 【多种设计模式】
=> 架构【服务器集群】
    -6:如果想成为合格的软件工程师:那就花时间,来研究下设计模式,是非常必要的。

3.:内容 & 授课方式:

   1)课程亮点和授课方式:

   2)建造者模式,讲解流程:








二.:七大设计原则介绍(5~22) 七大设计原则 介绍:

   1)设计模式的目的:
  在 软件编写过程中,程序员面临着来自 【耦合性、内聚性、可维护性、可拓展性、重用性、灵活性】 等多方面的挑战。设计模式,是为了让 程序(软件),具有更好的:
    -1:代码复用性:即:相同功能的代码,不用多次编写。
    -2:可读性:即:编程规范性,便于其他程序员的阅读和理解。
    -3:可拓展性(可维护性):即:当需要增加新的功能时,非常方便,成本低。
    -4:可靠性:即:当新增加功能后,对原来功能不会造成影响。
    -5:根本目的:使程序呈现高内聚、低耦合的特性:

   2)分析金句:
  1、设计模式,包含了面向对象的精髓,“懂了设计模式,你就懂了面向对象分析 和 设计(OOA/D)的精要”
  2、C++ 老手 和 新手的区别,就是前者手臂上,有很多伤疤。

   3)设计模式原则,其实就是:程序员在编程时,应当遵守的原则,也是各种设计模式的基础(即:设计模式为什么这样设计的依据)

   4)设计模式常用的七大原则有:
    -1:单一职责原则:
    -2:接口隔离原则:
    -3:依赖倒转原则:(依赖倒置原则)
    -4:里氏替换原则:
    -5:开闭原则:
    -6:迪米特法则:
    -7:合成复用原则:

1.:单一职责原则:(SimpleResponsibility)

   1)基本介绍:
    -1:是对类来说的,即:一个类,应该只负责一项职责:
  1、如类A负责两个不同职责:职责1、职责2。
  2、当职责1需求变更而改变A时,可能造成职责2执行错误。
  3、所以需要将类A的粒度,分解为 A1、A2。

   2)应用实例:使用 3个方案,进行分析:
    -1:以交通工具 案例讲解:
    -2:看老师代码演示:
    -3:方案1【分析说明】

public class Singleresponsility01 {

    public static void main(String[] args) {
        Vehicle vehicle = new Vehicle();
        vehicle.run("自行车");
        vehicle.run("摩托车");
        // 飞机就不合适,在此处运行
        vehicle.run("飞机");  
    }
}


class Vehicle {
    public void run(String vehicle) {
        System.out.println(vehicle + ":在公路上运行");
    }
}

    -4:方案2【分析说明】

public class Singleresponsility02 {

    public static void main(String[] args) {

        RoadVehicle roadVehicle = new RoadVehicle();
        roadVehicle.run("汽车");

        AirVehicle airVehicle = new AirVehicle();
        airVehicle.run("飞机");
    }
}


class RoadVehicle {
    public void run(String vehicle) {
        System.out.println(vehicle + ":在 公路上运行。");
    }
}

class AirVehicle {
    public void run(String vehicle) {
        System.out.println(vehicle + ":在 天上运行。");
    }
}

    -5:方案3【分析说明】

public class Singleresponsility03 {
    public static void main(String[] args) {
    
        Vehicle03 vehicle = new Vehicle03();
        vehicle.run("汽车");
        vehicle.runAir("飞机");
    }
}


class Vehicle03 {
    public void run(String vehicle) {
        System.out.println(vehicle + ":在公路上运行");
    }

    public void runAir(String vehicle) {
        System.out.println(vehicle + ":在天上运行");
    }
}

   3)单一职责原则,注意事项和细节:
    -1:降低类的复杂度:一个类,只负责一项职责。
    -2:提高类的可读性,可维护性:
    -3:降低变更,引起的风险:
    -4:通常情况下,我们应当遵守单一职责原则:只有逻辑足够简单,才可以在代码级,违反单一职责原则。只有类中方法数量足够少,可以在方法级别,保持单一职责原则。

2.:接口隔离原则:(Interface Segregation Principle)

   1)基本介绍:
    -1:客户端,不应该依赖它不需要的接口:即一个类对另一个类的依赖,应建立在最小的接口上。
    -2:先看一张图:

(1)A类,通过 Interface1,会依赖(使用)B类。
(2)但是 A中,只会使用到接口的 1 方法。(要使用 B类已经实现的 1方法)。(1)C类,通过 Interface1,会依赖(使用)D类。
(2)但是 C中,只会使用到接口的 2 方法。(要使用 D类已经实现的 2方法)。

    -3:编码完成:

interface Interface01 {
    void f1();
    void f2();
}

class B implements Interface01 {
    @Override
    public void f1() {
        System.out.println("B类实现了:f1()");
    }
    @Override
    public void f2() {
        System.out.println("B类实现了:f2()");
    }
}

class D implements Interface01 {
    @Override
    public void f1() {
        System.out.println("D类实现了:f1()");
    }
    @Override
    public void f2() {
        System.out.println("D类实现了:f2()");
    }
}

// A 类,通过接口 Interface01 依赖(使用)B类,但是只会用到 2 方法
class A {
    public void depend1(Interface01 interface01) {
        interface01.f1();
    }
}

// C类,通过接口 Interface01 依赖(使用)D类,但是只会用到 2 方法
class C {
    public void depend2(Interface01 interface01) {
        interface01.f2();
    }
}

    -4:类A 通过 接口interface01 依赖类B;类C通过接口Interface依赖类D:
  如果接口 Interface01 对于类A 和 类C 来说,不是最小接口。
  那么 类B 和 类D,必须去实现它们不需要的方法。
   2)上面传统方法出现的问题,如何使用 隔离原则进行改进?:
    -1:按隔离原则,应当是这样处理:
  将接口 Interface01 拆分为独立的 2个接口。
  类A 和 类C,分别与他们需要的接口建立依赖关系。也就是采用接口隔离原则。
    -2:接口 Interface1 中出现的方法,根据实际情况,拆分为 2个接口
    -3:代码实现:
  A 使用 B -> B 实现了 Interface01
  C 使用 D -> D 实现了 Interface02

public class InterfaceSegregationPrinciple01 {

    public static void main(String[] args) {
        B b = new B();
        A a = new A();
        a.depend1(b); // 输出:B类实现了:f1()

        C c = new C();
        D d = new D();
        c.depend2(d); // 输出:D类实现了:f2()
    }
}

interface Interface01 {
    void f1();
}

interface Interface02 {
    void f2();
}

class B implements Interface01 {
    @Override
    public void f1() {
        System.out.println("B类实现了:f1()");
    }
}

class D implements Interface02 {
    @Override
    public void f2() {
        System.out.println("D类实现了:f2()");
    }
}

class A {
    public void depend1(Interface01 interface01) {
        interface01.f1();
    }
}

class C {
    public void depend2(Interface02 interface02) {
        interface02.f2();
    }
}


3.:依赖倒转原则:(Dependence Inversion Principle)

   1)基本介绍:依赖倒转原则是指:(类似于面向接口编程思想)
    -1:高层模块,不应该依赖底层模块,二者都应该依赖其抽象。
    -2:抽象不应该依赖细节,细节应该依赖抽象。
    -3:依赖倒转(倒置)的中心思想,是面向接口编程。
    -4:依赖倒转原则,是基于这样的设计理念:
  1、相对于细节的多变性,抽象的东西要稳定的多。
  2、以抽象为基础搭建的架构,比 以细节为基础的架构,要稳定的多。
  3、在 Java 中,抽象指的是接口 或者 抽象类,细节就是具体的实现类。
    -5:使用接口 或 抽象类的目的是:制定好规范,而不涉及任何具体的操作,把展现细节的任务,交给他们的实现类去完成。

   2)依赖倒转原则,需要注意事项和细节:
    -1:底层模块,尽量都要有抽象类 或 接口,或者两者都有,程序稳定性更好。
    -2:变量的声明类型,尽量是抽象类或接口:这样我们的变量引用和实际对象间,就存在一个缓冲层,利于程序拓展和优化。
    -3:继承时:应遵循 里氏替换原则

   3)应用实例:
    -1:请编程完成 Person 类中,接收消息的功能:
    -2:实现方案 1 + 分析说明

public class DependenceInversion {

    public static void main(String[] args) {
        Email email = new Email();
        Person person = new Person();
        person.receive(email);
    }

}

class Email {
    public String getInfo() {
        return "电子邮件信息:HelloWorld";
    }
}


class Person {
    public void receive(Email email) {
        System.out.println(email.getInfo());
    }
}

    -3:实现方案 2 + 分析说明
    -3.1:上面实现方式,存在的问题:
  1、如果我们获取的对象是微信、短信等,则要新增类,同时 Person 也要增加,响应的接收方法。
    -3.2:解决思路:
  1、引入一个 抽象的接口:IReceiver,表示接收者,这样 Preson 与接口发生依赖。
  2、因为 Email、微信等,都属于接收的范围。他们各自实现 IReceiver 接口就ok。
  3、这样我们就符合,依赖倒转原则。

package com.example.designpattern.com.atguigu.principle.dependenceInversionPrinciple;


public class DependenceInversion {

    public static void main(String[] args) {
        Person person = new Person();
        person.receive(new Email());
        person.receive(new WeiXin());
    }
}

interface IReceiver {
    String getInfo();
}

class Email implements IReceiver {
    @Override
    public String getInfo() {
        return "电子邮件信息:HelloWorld";
    }
}

class WeiXin implements IReceiver {
    @Override
    public String getInfo() {
        return "微信信息:WeiXin";
    }
}


class Person {
	// 这里是对接口的依赖
    public void receive(IReceiver iReceiver) {
        System.out.println(iReceiver.getInfo());
    }
}

   4)依赖关系传递的,三种方式 和 应用案例:
    -1:接口传递:应用案例代码

public class De {
    public static void main(String[] args) {
        OpenAndClose openAndClose = new OpenAndClose();
        openAndClose.open(new Changhong());
    }
}

interface ITV{  // 抽象接口
    void play();
}

interface IOpenAndClose{ // 抽象接口
    void open(ITV itv);	// 抽象方法,接收的是:接口
}

class OpenAndClose implements IOpenAndClose {

    @Override
    public void open(ITV itv) {
        itv.play();
    }
}

    -2:构造方法传递:应用案例代码

interface ITV {  // 抽象接口
    void play();
}

interface IOpenAndClose {   // 抽象接口
    void open();
}

class OpenAndClose implements IOpenAndClose {

    public ITV itv;

    // 使用构造方法,依赖传递
    public OpenAndClose(ITV itv) {
        this.itv = itv;
    }

    @Override
    public void open() {
        itv.play();
    }
}

    -3:setter 方式传递:应用案例代码

interface ITV {  // 抽象接口
    void play();
}

interface IOpenAndClose {   // 抽象接口
    void open();
    void setItv(ITV itv);
}

class OpenAndClose implements IOpenAndClose {

    public ITV itv;

    // 使用 setter 方法,传递依赖
    @Override
    public void setItv(ITV itv) {
        this.itv = itv;
    }

    @Override
    public void open() {
        itv.play();
    }
}

4.:里氏替换原则:

   1)
   2)
   3)
   4)
   5)
   6)

5.:开闭原则:

   1)
    -1:
    -2:
    -3:
    -4:
    -5:
   2)
    -1:
    -2:
    -3:
    -4:
    -5:
   3)
    -1:
    -2:
    -3:
    -4:
    -5:
   4)
    -1:
    -2:
    -3:
    -4:
    -5:
   5)
    -1:
    -2:
    -3:
    -4:
    -5:
   6)
    -1:
    -2:
    -3:
    -4:
    -5:

6.:迪米特法则:

   1)
    -1:
    -2:
    -3:
    -4:
    -5:
   2)
   3)
   4)
   5)
   6)

7.:合成复用原则:

   1)
   2)
   3)
   4)
   5)
   6)
    -1:
    -2:
    -3:
    -4:
    -5:




三.:UML 类图(23~27) 1.:

   1)
   2)
   3)
   4)
   5)
   6)

2.:

   1)
   2)
   3)
   4)
   5)
   6)

3.:

   1)
   2)
   3)
   4)
   5)
   6)

4.:

   1)
   2)
   3)
   4)
   5)
   6)

5.:

   1)
   2)
   3)
   4)
   5)
   6)

6.:

   1)
   2)
   3)
   4)
   5)
   6)
    -1:
    -2:
    -3:
    -4:
    -5:




四.:(~) 1.:

   1)
   2)
   3)
   4)
   5)
   6)

2.:

   1)
   2)
   3)
   4)
   5)
   6)

3.:

   1)
   2)
   3)
   4)
   5)
   6)

4.:

   1)
   2)
   3)
   4)
   5)
   6)

5.:

   1)
   2)
   3)
   4)
   5)
   6)

6.:

   1)
   2)
   3)
   4)
   5)
   6)
    -1:
    -2:
    -3:
    -4:
    -5:




五.:(~) 1.:

   1)
   2)
   3)
   4)
   5)
   6)

2.:

   1)
   2)
   3)
   4)
   5)
   6)

3.:

   1)
   2)
   3)
   4)
   5)
   6)

4.:

   1)
   2)
   3)
   4)
   5)
   6)

5.:

   1)
   2)
   3)
   4)
   5)
   6)

6.:

   1)
   2)
   3)
   4)
   5)
   6)
    -1:
    -2:
    -3:
    -4:
    -5:




六.:(~) 1.:

   1)
   2)
   3)
   4)
   5)
   6)

2.:

   1)
   2)
   3)
   4)
   5)
   6)

3.:

   1)
   2)
   3)
   4)
   5)
   6)

4.:

   1)
   2)
   3)
   4)
   5)
   6)

5.:

   1)
   2)
   3)
   4)
   5)
   6)

6.:

   1)
   2)
   3)
   4)
   5)
   6)
    -1:
    -2:
    -3:
    -4:
    -5:




转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/749242.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号