软件设计不是CRUD(11):低耦合模块设计理论——业务抽象:规划模块分层

上一篇文章《软件设计不是CRUD(10):低耦合模块设计理论——业务抽象:从需求中提取业务维度》本专题详细讲解了业务抽象的一个重要步骤:提取业务维度。本篇文章内容主要讲解在提取业务维度后,如何对应用程序中初步划分的各个功能模块进行分层规划。

1、为什么要进行模块分层

需要注意的是,在对应用程序的需求进行业务维度提取时,设计人员实际上还没有,也无法对应用程序最终如何划分功能模块进行明确。这是因为提取业务维度这件事情并不以划分模块为前提,而只是业务抽象设计的第一个工作。提取业务维度所需要的业务边界,也只是从设计人员对业务理解的角度出发、从设计人员经验角度出发的大致划分。

对应用系统中初步划分的功能模块进行分层规划,将形成对初步划分的功能模块进行调整和验证的依据,以便形成更准确的模块划分和模块边界。所谓调整就是将凭直觉、凭经验进行初步划分的模块按照分层原则进行再拆分、再合并、再添加甚至进行删除。所谓验证,就是验证这些完成分层的模块是否能匹配原始的需求、是否能匹配未来可能变化的需求点。

模块分层也是保证模块间低耦合强度的前提,是明确模块间调用关系的前提。注意,这里描述的因果关系:因为满足了模块分层的基本原则,所以才能保证模块间低耦合强度。而不是一些读者理解的:因为保证了模块间的低耦合强度,所以模块自然就进行了分层。这个因果关系存在的本质原因是模块间的依赖关系可以在从设计层面上出发,不受原始业务需求限制,随意地进行依赖倒转。

2、模块分层的基本原则

以下是基于模块分层原则,完成规划的应用程序功能模块分层示意图:
在这里插入图片描述

注意:上图中所描述的各个“分层区域”不存在特定意义,只是为了便于读者对模块分层后的效果进行理解而进行的一种归纳。可以看到进行了有效的模块分层规划后,所有模块间的依赖都是单向的,并且处于同一分层区域上的两个(或多个)模块很少存在依赖关系。

原始需求对模块的分层规划具有指导性作用,但并不起决定性作用。因为模块设计和原始需求通过业务抽象进行了设计隔离。具体的效果表现为:虽然原始需求的描述中,要求A模块工作过程中需要调用B模块的功能(例如:原始需求是,出库业务完成后会调用订单模块,将当前出库单对应的订单状态变为“已完成”),但是进行模块分层规划后,B模块所处分层完全可能在A模块所处分层之上(订单模块在出库模块之上)。模块分层的主要原则有:

  • 变化风险越大的模块,分层位置越靠上
  • 模块间的依赖关系一定是单向的,且一定不存在循环依赖
  • 下层模块“看不到”上层模块
  • 上层模块可以调用、扩展下层模块的功能

2.1、业务屈服度和业务变化风险

2.1.1、业务屈服度

业务屈服度是指当一个既有功能模块的需求变化达到何种程度后,功能模块的代码就必须进行修改,否则该功能模块就不再能满足业务要求。这种“不再能满足业务要求”的变化可以由业务维度发生变化导致,也可以由功能模块的控制逻辑发生改变导致。所以也可以对以上描述做如下理解:

功能模块A之所以叫做功能模块A,是因为具有X,Y,Z这三个业务维度,并有一个固定的控制逻辑将这三个业务维度联系起来,构成一个完整的工作过程。当功能模块的业务维度需要新增,且已存在的业务维度和新的业务维度无法进行合并时;又或者当目前的控制逻辑需要做出过大调整,不能再按照原来的顺序将业务维度联系起来时,需求变化的程度就超过了功能模块可以适应变化的最大设计强度,

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/657329.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【lesson2】定长内存池的实现

文章目录 介绍定长内存池的设计定长内存池的实现需要成员变量需要的成员函数定长内存池结构定长内存池Delete(释放空间)的实现定长内存池New(申请空间)的实现 定长内存池的实现完整版 介绍 作为程序员(C/C)我们知道申请内存使用的…

Zookeeper实现分布式队列

目录 Zookeeper分布式队列 普通方式实现 设计思路 具体实现 使用Curator实现 具体实现 注意事项 Zookeeper分布式队列 常见的消息队列有:RabbitMQ,RocketMQ,Kafka等。Zookeeper作为一个分布式的小文件管理系统,同样能实现简单的队列功…

【python】图形化开发pyqt6基本写法模板与基础控件属性方法整理

pyqt6的简介 首先呢Python有许多可以编写图形化界面的库,我们通常跟着教程的话最初会接触的tkinter,但是学习中会发现编写的图形化跟我们平常接触的软件有很大区别(简单来说就是丑)。 pyqt则是第三方库,在Python中算…

ETL怎么实现文件处理

在现代企业及各类组织的日常运作中,数据作为一种关键的信息资源,其管理和分析能力直接影响到决策效率与准确性。文件作为数据的主要载体,承载着从运营报告、客户记录、交易明细等各种类型的数据信息。这些海量且多样的文件数据在未经处理的情…

flask_django基于python的城市轨道交通公交线路查询系统vue

同时,随着信息社会的快速发展,城市轨道交通线路查询系统面临着越来越多的信息,因此很难获得他们对高效信息的需求,如何使用方便快捷的方式使查询者在广阔的海洋信息中查询,存储,管理和共享信息方面有效&…

C语言菜鸟入门·运算符(算数运算符,关系运算符,逻辑运算符,位运算符,赋值运算符,三目运算符)详细介绍

目录 ​编辑 1. 算术运算符 2. 关系运算符 3. 逻辑运算符 4. 位运算符 5. 赋值运算符 6. 杂项运算符 ↦ sizeof & 三元 6.1 sizeof() 6.2 &取地址运算符 6.3 * 6.4 三目运算符 7. 运算符优先级 运算符是一种告诉编译器执行…

ElementUI组件:Link 文字链接

Link 文字链接 点击下载learnelementuispringboot项目源码 效果图 el-link.vue页面效果图 项目里el-link.vue文件代码 <script> export default {name: el_link }</script> <!--https://element.eleme.cn/#/zh-CN/component/link --> <template>&l…

嵌入式学习第十四天

1.结构体&#xff08;2&#xff09;: &#xff08;1&#xff09;结构体类型定义 &#xff08;2&#xff09;结构体变量的定义 &#xff08;3&#xff09;结构体元素的访问 &#xff08;4&#xff09;结构体的存储: 内存对齐: char 按照1字节对齐 …

C# OpenCvSharp DNN Gaze Estimation 视线估计

目录 介绍 效果 模型信息 项目 代码 frmMain.cs GazeEstimation.cs 下载 C# OpenCvSharp DNN Gaze Estimation 介绍 训练源码地址&#xff1a;https://github.com/deepinsight/insightface/tree/master/reconstruction/gaze 效果 模型信息 Inputs ----------------…

医院安全(不良)事件报告系统源码,不良事件处理的全过程管理,实现11大类不良事件类型的报告上报、流转审批、跟踪改进及统计分析功能。

医院安全&#xff08;不良&#xff09;事件报告系统源码&#xff0c;不良事件上报系统源码&#xff0c;PHP源码 医院安全&#xff08;不良&#xff09;事件报告系统提供11大类不良事件的上报、事件审核处理、时间按分析、事件跟踪与持续改进&#xff0c;事件提醒、权限控制、外…

聊聊DoIP吧

DoIP是啥? DoIP代表"Diagnostic over Internet Protocol",即互联网诊断协议。它是一种用于在车辆诊断中进行通信的网络协议。DoIP的目标是在现代汽车中实现高效的诊断和通信。通过使用互联网协议(IP)作为通信基础,DoIP使得诊断信息能够通过网络进行传输,从而提…

React通用后台模板

一. 项目初始化 1. 创建项目 环境 npm init vite 打开package.json,参考以下各模块版本: "dependencies": { "react": "^18.2.0", "react-dom": "^18.2.0", "react-redux": "^7.2.8", …

Security ❀ TCP异常报文详解

文章目录 1. TCP Out-Of-Order2. TCP Previous Segment Lost3. TCP Retransmission4. TCP Dup Ack XXX#X5. TCP Windows Update6. TCP Previous segment not captured7. 异常案例分析 TCP协议中seq和ack seq的联系&#xff1a; id4的http请求报文由客户端发向服务器&#xff0…

sqli-labs-master靶场训练笔记(1-22|新手村)

2024.1.21 level-1 &#xff08;单引号装饰&#xff09; 先根据提示建立一个get请求 在尝试使用单个单引号测试&#xff0c;成功发现语句未闭合报错 然后反手一个 order by 得到数据库共3列&#xff0c;-- 后面加字母防止浏览器吃掉 -- 操作&#xff08;有些会&#xff09…

maven helper 解决jar包冲突方法

一 概要说明 1.1 说明 首先&#xff0c;解决idea中jar包冲突&#xff0c;使用maven的插件&#xff1a;maven helper插件&#xff0c;它能够给我们罗列出来同一个jar包的不同版本&#xff0c;以及他们的来源&#xff0c;但是对不同jar包中同名的类没有办法。 1.2 依赖顺序 …

Spring | Spring的“数据库开发“ (Srping JDBC)

目录&#xff1a; Spring JDBC1.Spring JDBC的核心类 ( JdbcTemplate类 )2.Srping JDBC 的配置3.JdbcTemplate类的“常用方法”execute( )&#xff1a;直接执行“sql语句”&#xff0c;没有返回值update( ) &#xff1a;“增删改”&#xff0c;返回 “影响的行数”query( ) : “…

双链表的基本知识以及增删查改的实现

满怀热忱&#xff0c;前往梦的彼岸 前言 之前我们对单链表进行了非常细致的剖析&#xff0c;现在我们所面临的则是与之相对应的双链表&#xff0c;我会先告诉诸位它的基本知识&#xff0c;再接着把它的增删查改讲一下&#xff0c;ok&#xff0c;正文开始。 一.链表的种类 我…

其他发现:开源数据可视化分析工具DataEase介绍文档

一、 简介 DataEase 是开源的数据可视化分析工具&#xff0c;帮助用户快速分析数据并洞察业务趋势&#xff0c;从而实现业务的改进与优化。DataEase 支持丰富的数据源连接&#xff0c;能够通过拖拉拽方式快速制作图表&#xff0c;并可以方便地与他人分享。 二、 优势 1、 开…

STM32学习笔记二——STM32时钟源时钟树

目录 STM32芯片内部系统架构详细讲解&#xff1a; 1.芯片内部混乱电信号解决方案&#xff1a; 2.时钟树&#xff1a; 1.内部RC振荡器与外部晶振的选择 2. STM32 时钟源 3.STM32中几个与时钟相关的概念 4.时钟输出的使能及其流程 5.时钟设置的基本流程 时钟源——单片机…

Java多线程--同步机制解决线程安全问题方式二:同步方法

文章目录 一、同步方法&#xff08;1&#xff09;同步方法--案例11、案例12、案例1之同步监视器 &#xff08;2&#xff09;同步方法--案例21、案例2之同步监视器的问题2、案例2的补充说明 二、代码及重要说明&#xff08;1&#xff09;代码&#xff08;2&#xff09;重要说明 …