系统架构设计师常见高频考点总结之软件工程
1.软件工程与软件过程模型核心考点
1.1. 软件过程模型速记总结表
| 模型名称 | 核心关键词(看到这些词就选它) | 适用场景 | 关键缺点 |
| 瀑布模型 | 线性、文档驱动、需求冻结 | 需求明确、二次开发 | 需求变化适应差 |
| V模型 | 测试与开发对应、验收测需求 | 高可靠性(航天/医疗) | 测试介入晚 |
| 原型模型 | 界面、用户参与、抛弃/演化 | 需求不明确 | 容易变成“补丁”系统 |
| 螺旋模型 | 风险分析 | 大型、复杂、高风险 | 成本高 |
| 增量模型 | 拼图、分批交付、第一个可运行 | 需尽早使用系统 | 容易退化成边做边改 |
| XP 极限编程 (敏捷) | 结对编程、TDD、重构 | 需求模糊、小团队 | 文档少 |
| Scrum (敏捷) | 冲刺、Backlog、站会 | 需求模糊、管理聚焦 | 需自组织能力强 |
| UP(统一过程) | 严谨“用例 (Use Case)”文档为中心 | ||
| RUP | 用例驱动、以体系结构为中心、迭代和增量 | 跨度极广的各类综合性项目、存在较高潜在风险的项目、需求在初期无法完全明确或会不断变化的项目 |
1.2 原型开发过程
原型开发分为三类:抛弃式原型开发利用原型验证和澄清系统的需求描述,重新构造系统:演化式原型开发逐步改进和细化原型,将原型进化直至产生出目标系统;增量式原型开发在建立软件总体设计的基础上,采用增量开发方法,使原型成为最终系统。
1.3 敏捷开发过程
1. 开放式源码
关键字: 地域上分布很广、查错排障的高度并行性。
2. 功用驱动开发方法(FDD)
关键字: 首席程序员、“类”程序员。
3. 水晶系列
关键字: 最少纪律约束、产出效率与易于运作上达到平衡。
4. 自适应软件开发(ASD)
关键字: 猜测、合作与学习(三个非线性的、重叠的开发阶段)。
5. 极限编程(XP)
关键字: 结对编程、持续集成、代码驱动、费用控制严格。
解析: XP是敏捷中最引人瞩目的,非常强调结对工作和及早发现错误的“冒烟测试”环境。
6. SCRUM开发方法
关键字: Sprint(短迭代周期)、每日站立会议、燃尽图、明确定义了的可重复的方法过程(优先考虑商业价值)。![]()
Scrum经常作为大题或选择题出现。核心角色是Scrum主管、产品负责人和开发团队。强调把大需求拆分成短周期(Sprint)来完成
1.4 RUP开过程
1. RUP 的三大核心特点: 与其他软件开发过程相比,RUP 具有自己鲜明的特征,它可以概括为三个词:
- 用例驱动: 用例是驱动RUP整个开发过程的基础,从需求获取到设计、实现和测试,都围绕用例展开。
- 以体系结构为中心: 强调在开发的早期阶段就要建立一个稳定可执行的软件架构。
- 迭代和增量: 将整个开发过程分为多个小的迭代周期,逐步交付并完善系统。
2. RUP 的四个连续阶段: RUP 把软件开发生存周期划分为多个循环,每个循环生成产品的一个新的版本。每个循环依次由4个连续的阶段组成,这是历年真题中非常高频的考点,您需要熟记它们各自的核心任务:
- 初始阶段: 定义最终产品视图和业务模型,并确定系统范围(明确项目边界)。
- 细化阶段: 设计及确定系统的体系结构,制定工作计划及资源要求(分析问题领域,淘汰最高风险元素)。这正是本题所考查的阶段。
- 构造/构建阶段: 构造产品,开发剩余的构件和功能,并继续演进需求、体系结构、计划直至产品提交。
- 移交/交付阶段: 把产品提交给最终用户使用,包括测试、Beta版本发布、培训等,确保软件对最终用户可用。
💡 备考小贴士: 在应对此类题目时,记住几个核心匹配词:
- 看到“确定范围/业务模型” ➔ 选 初始阶段
- 看到“体系结构/架构设计/计划资源” ➔ 选 细化阶段
- 看到“开发构件/编码实现” ➔ 选 构造阶段
- 看到“交付用户/Beta测试” ➔ 选 移交阶段
1.5 螺旋模型
螺旋模型把整个软件开发流程分成多个阶段,每一个阶段都由目标设定、风险分析、开发和有效性验证以及评审构成。
1.6 应试技巧
选型题:先看需求明不明确。
明确 ↔ 瀑布/V模型。
不明确 ↔ 原型/敏捷/螺旋。(螺旋、敏捷都是从原型发展来的)
看到“风险” ↔ 螺旋
看到“尽快交付部分功能” ↔ 增量(RUP强调采用迭代和增量,方式来开发软件)
V模型题:画出V图,找水平对应线。
2、 关键图表

2.1 结构化分析方法
- 数据流图(DFD): 表示功能模型,展现业务处理过程和数据的流动方向。
- 实体联系图(E-R图): 表示数据模型,描述数据对象极其相互关联。
- 状态转换图(STD): 表示行为模型(或状态模型),描述系统的动态行为。
数据流图和数据字典在需求分析和设计阶段的作用
- 数据流图分析阶段:建立系统的功能模型,从而完成需求分析。
- 数据流图设计阶段:为模块划分与模块之间接口设计提供依据。
- 数据字典在分析与设计阶段的作用为:是所有人员工作的依据,统一的标准。它可以确保数据在系统中的完整性和一致性。
- 结构化分析强调自顶向下的系统分解,核心是使用数据流图(DFD)来建模系统,强调数据在系统中的流动与处理过程
- 结构化设计关注模块的 低耦合、高内聚,其中非直接耦合是最低程度的耦合
2.2 面向对象方法(UML统一建模语言)
- 静态/结构模型(描述系统静态结构):
- 类图
- 包图: 表示的软件体系结构图
- 部署图:描述系统的物理结构,即软件组件在硬件节点(服务器、终端、网络设备等)上的部署方式。部署图展示了系统的运行环境,包括节点、连接关系以及组件的分布,是物理建模中最重要的 UML 图
- 对象图
- 动态/行为模型(描述系统动态行为):
- 用例图:构建用例模型一般需要经历4个阶段,分别是识别参与者、合并需求获得用例、细化用例描述和调整用例模型,其中前三个阶段是必需的

- 状态图:主要用于描述一个特定对象在其生存期间的动态行为,表现该对象所经历的状态序列,以及引起状态转移的事件和因状态转移而伴随的动作。
- 活动图:展现了在系统内从一个活动到另一个活动的流程,强调对象之间的控制流程。它主要用于描述系统的工作流程和并发行为。Activity 可以再分割,泳道分配给各个对象,动作状态是UML活动图中最基本的、不可再分的执行单元,具有原子性。分支表示流程根据条件进行判断选择,是一种控制流的条件分支。分叉表示流程被并行分成多个执行线程,是多线程并发的开始。

- 顺序图(序列图) / 通信图(协作图)
顺序图中的消息类型包括:同步消息、异步消息、返回消息和自关联消息
“读者借阅图书”场景中的消息类型可能包括:同步消息(如读者提交借阅请求,系统响应借阅成功或失败)、异步消息(如读者提交预约图书请求)、返回消息(如系统返回图书的详情)。
- 用例图:构建用例模型一般需要经历4个阶段,分别是识别参与者、合并需求获得用例、细化用例描述和调整用例模型,其中前三个阶段是必需的
“结构化”和“面向对象” 如果将这两种方法结合, 首先使用结构化方法进行自顶向下的整体划分,然后再自底向上地采用面向对象方法开发系统
2.3 其他独立的流程建模工具(非UML)
- BPMN(业务流程模型和符号): 专门用于业务流程建模的独立标准规范。
- Petri网:是一种基于图论的形式化建模方法,能够同时描述控制流与数据流。它非常适合表示嵌入式系统、实时系统中的并发、同步与通信机制。
- 程序流程图(PFD): 描述处理过程的控制流,属于物理建模(系统设计)阶段的图形

2.4 综合应用
面向对象(OOD)的分析模型主要由顶层架构图、用例与用例图和领域概念模型构成:设计模型则包含以包图 表示的软件体系机构图、以交互图表示的用例实现图、完整精确的类图、描述复杂对象的状态图和用以描述流程化处理过程的活动图等。
总结你的记忆口诀:
分析阶段(找业务,静态图): 宏观架构 + 用户用例 + 领域概念。
设计阶段(写代码,动态图): 架构变包,用例变交互,概念变精确类。
动态补充: 单个对象看状态,流水线看活动。
3. 质量属性
3.1 质量属性六要素
描述一个质量属性必须包含六个要素(重点记忆理解)
刺激源:生成刺激的实体。
刺激:当刺激到达系统时需要考虑的条件或事件(突发事件/请求到)
环境 :系统当时的状态。
制品 :被激励的系统或系统的一部分。
响应:刺激到达后采取的行动。
响应度量:对响应进行度量的方式
在系统设计时,客户提出了新增 API 接口的开发工作需要在 3 个工作日内完成。
- 刺激源:客户
- 刺激:新增
- 环境:系统设计时
- 制品:API 接口
- 响应:完成 API 接口新增
- 响应度量:3 个工作日
3.2 传统质量特性
口诀:能用靠安,修修测测。
-
能:性能
-
用:可用性
-
靠:可靠性
-
安:安全性
-
修:可修改性
-
测:可测试性
- 可修改性↔ 关键词:修改、替换、二次开发、添加新功能 ↔ 策略:接口-实现分离、信息隐藏、抽象接口、运行时注册。
- 可用性 ↔ 关键词:断电、宕机、故障、重启、X秒内恢复 ↔ 策略:心跳、Ping/Echo、主动/被动冗余、选举、检查点/回滚。
- 性能 ↔ 关键词:响应时间 (X秒内响应)、吞吐量、并发数 ↔ 策略:引入并发、资源调度、优先级队列、增加计算资源。
- 安全性 ↔ 关键词:抵挡恶意入侵、授权、加密、报警记录 ↔ 策略:追踪审计、用户认证/授权、限制访问、入侵检测。
- 可测试性 ↔ 关键词:远程调试、错误诊断、设置断点 ↔ 策略:记录/回放、内置监控器。
3.2.1 性能
• 定义:系统的响应能力,即要经过多长时间才能对某个事件做出响应
• 常见场景描述:
◦ “在并发用户数量为1000人时,用户的交易请求需要在0.5秒内得到响应”。
◦ “系统处理每秒50个交易请求”6。
• 常用架构策略:
◦ 资源需求:减少计算开销、控制资源使用、限制执行时间。
◦ 资源管理:引入并发机制、增加计算资源(如增加服务器)、多副本。
◦ 资源仲裁:队列调度(先进先出、优先级队列)。
性能评价程序的准确程度排序 在测试新系统的性能时,用户通常需要依靠评价程序来测试机器的性能。根据程序的真实性和覆盖面,这些评价程序的评测准确程度由高到低依次递减的顺序为: 真实程序 > 核心程序 > 小型基准程序 > 合成基准程序。
3.2.2 可用性
• 定义:系统在能够正常运行的时间比例。
• 常见场景描述:
◦ “主站点断电后,需要在3秒内将访问请求重定向到备用站点”。
◦ “系统故障后,需在2分钟内恢复运行”。
• 常用架构策略:
◦ 错误检测:心跳、Ping/Echo、异常检测。
◦ 错误恢复:主动冗余、被动冗余、表决、检查点/回滚、状态再同步。
◦ 错误预防:进程监视器、事务。
可用性通常用平均无故障时间(MTBF)和平均故障修复时间(MTTR)来衡量
MTTF (Mean Time To Failure):平均无故障时间(寿命)。
MTTR (Mean Time To Repair):平均修复时间。
MTBF (Mean Time Between Failures):平均故障间隔时间。
公式:𝑀𝑇𝐵𝐹=𝑀𝑇𝑇𝐹+𝑀𝑇𝑇𝑅
结论:在现代系统中,因为修复时间 MTTR(通常几小时)远小于运行时间 MTTF(通常几千小时),所以在计算时常认为
𝑀𝑇𝐵𝐹≈𝑀𝑇𝑇𝐹。
3.2.3 可靠性
• 定义:系统在规定的时间内及规定的环境条件下,完成规定功能的能力,就是系统无故障运行的概率
• 常见场景描述:
◦ “系统在发生故障时,能够维持规定的性能级别”。
◦ “系统能够避免因错误的发生而导致失效”。
◦ 注:在软考中,可靠性常与可用性关联,但可靠性更侧重于“无错运行”,而可用性侧重于“故障后快速恢复”。
• 常用架构策略:
◦ 容错、冗余技术、双机容错、集群技术。
3.2.4. 安全性
• 定义:系统向合法用户提供服务的同时能够阻止非授权用户使用的企图或拒绝服务的能力。
• 常见场景描述:
◦ “用户的信用卡支付必须保证99.999%的安全性”。
◦ “系统应该能够抵挡恶意用户的入侵行为,并进行报警和记录”。
• 常用架构策略:
◦ 抵抗攻击:用户身份验证、用户授权、加密(维护数据机密性)、限制访问。
◦ 检测攻击:入侵检测系统。
◦ 从攻击中恢复:审计追踪(追踪审计)、恢复状态。
3.2.5. 可修改性
• 定义:能够快速地以较高的性能价格比对系统进行变更的能力。它包含可维护性、可扩展性、结构重组和可移植性。
• 常见场景描述:
◦ “更换数据库(如从MSSQL换为Oracle),要求在1周内完成”。
◦ “系统需要对Web界面风格进行修改,修改工作必须在4人月内完成”。
◦ “增加新的支付接口不影响现有架构”。
• 常用架构策略:
◦ 局部化修改:高内聚低耦合、维持语义一致性。
◦ 防止连锁反应:信息隐藏、接口与实现分离、使用中介(如仲裁者)。
◦ 推迟绑定时间:运行时注册、配置文件、多态。
3.2.6 可测试性
• 定义:指软件发现故障并隔离、定位其故障的能力,以及在一定时间和成本下进行测试的能力。
• 常见场景描述:
◦ “系统需要为后端工程师提供远程调试接口,并支持远程调试”。
◦ “系统能够进行远程错误诊断”。
• 常用架构策略:
◦ 记录/回放、接口与实现分离、内置监控器。
3.3 ISO/IEC 9126标准质量特性
软考有时也会直接考察 ISO/IEC 9126 标准中的六大质量特性
1.功能性 2.可靠性 3. 易用性 4. 效率 5. 维护性 6. 可移植性
口诀:公公靠椅笑喂姨。
这个口诀利用了六个特性的首字谐音,构建了一个滑稽的场景:
公公 (Gōnggong) -> 对应 功能性 (Gōng)
靠 (Kào) -> 对应 可靠性 (Kě kào)
椅 (Yǐ) -> 对应 易用性 (Yì)
笑 (Xiào) -> 对应 效率 (Xiào)
喂 (Wèi) -> 对应 维护性 (Wéi)
姨 (Yí) -> 对应 可移植性 (Yí)
易用性 的常见“刺激”包括:
想要学习系统特性
有效使用系统
使错误的影响最低
适配系统
对系统满意
这些描述均对应用户在使用系统时的容易程度、学习曲线及满意度,属于易用性的范畴。
4. 需求工程
需求工程 的两个核心分支:需求开发 和 需求管理 的区别。这是系统架构设计师中的高频考点。很多考生容易混淆这两个概念,认为它们是一回事。其实它们是相辅相成但职责完全不同的两个过程。
4.1. 核心概念拆解
-
需求开发
-
核心动作:产出。
-
目的:从无到有,把模糊的用户想法变成清晰的文档。
-
包含四个阶段:
-
需求获取 :收集用户想要什么。
-
需求分析:分析这些需求合不合理,有没有冲突。
-
需求定义 :写成 SRS(需求规格说明书)。
-
需求验证:找用户确认写得对不对。
-
-
-
需求管理
-
核心动作:控制与追踪。
-
目的:对于软件需求,必须建立基线以进行控制,软件计划、产品和活动必须与软件需求保持一致
-
核心内容:
-
变更控制:问题分析与变更描述,变更分析与成本计算,变更实现
-
版本控制:这是第几版需求?
-
需求追踪:双向跟踪
-
状态跟踪:需求是“已建议”、“已批准”还是“已实现”?
-
-
4.2. 选项逐一解析
A. 所谓需求管理是指对需求开发的管理 (❌ 错误)
解析:需求管理不是“管人”或“管开发过程”,而是管理“需求”这个产物本身(及其变更和生命周期)。它们是并行的活动。
B. 需求管理包括需求获取、需求分析、需求定义和需求验证 (❌ 错误)
解析:这四个步骤属于 需求开发 的范畴。这是典型的张冠李戴。
C. 需求开发是将用户需求转化为应用系统成果的过程 (❌ 错误/不严谨)
解析:需求开发的结果是 “需求规格说明书 (SRS)” 等逻辑文档,而不是最终的 “应用系统成果” (即运行的软件)。将需求转化为软件成果的过程属于“系统设计”和“系统实现/编码”。
D. 在需求管理中,要求维持对原有需求和所有产品构件需求的双向跟踪 (✅ 正确)
解析:这是需求管理的核心定义之一。
正向跟踪 :用户需求 -> 需求规格 -> 架构设计 -> 代码 -> 测试用例。(保证所有需求都被实现了)
反向跟踪:代码/测试用例 -> 需求规格 -> 用户需求。(防止做“镀金”操作,即防止开发了用户没要求的功能;确代码是为了哪个需求写的)。
4.3.知识点总结 (必背)
需求基线作为开发基础,防止需求蔓延 ;需求分析工具分为基于自然语言/图形描述的工具和基于形式化需求定义语言的工具 。
外部设计处于软件设计的开始阶段,主要是按系统需求说明来确定此系统的软件结构和对应于系统需求说明,设计出各个功能部分的功能和接口。内部设计处于软件工程中的概要设计阶段,按照外部设计中确立的系统软件结构,来细化此系统各个功能部件以及各个部件接口的设计,并且详细给出各个功能部件详细的数据输入、输出设计。内部设计细化外部设计中的各种功能。
| 维度 | 需求开发 (RD) | 需求管理 (RM) |
| 侧重点 | “生孩子” (把需求生出来) | “养孩子” (管好需求,别让他长歪了) |
| 包含步骤 |
1. 需求获取 2. 需求分析 3. 需求定义 4. 需求验证 |
1. 变更控制 2. 版本控制 3. 需求跟踪 (双向) 4. 状态跟踪 (变版需装) |
| 产出物 | 需求规格说明书 (SRS) | 需求跟踪矩阵 (RTM)、变更记录 |
| 典型考点 | 验证是找用户确认,不是测试代码 | 双向跟踪:正向查漏(防遗漏)反向查错(防镀金) |
一句话助记:
开发负责“生”(获取、分析、定义、验证),管理负责“养”(变更、版本、跟踪)。
5、 系统安全性设计
遵循 “纵深防御” 原则,至少掌握以下三个层面的手段:
访问控制: 认证和授权
数据保护: 加密和完整性
安全审计: 日志监控:记录谁在什么时间做了什么,用于事后追责和异常发现。
6. 软件测试
在软件开发的不同阶段 (6.1, 6.2),我们要么让代码跑起来(动态),要么不跑(静态 6.6)。跑起来的时候,底层我们用白盒和 BRO (6.3, 6.7) 的技术做单元测试,上层我们用黑盒 (6.4) 的技术做系统和确认测试。而在这个漫长的过程中,只要代码一改,我们就得立刻触发回归测试 (6.5)
6.1.关于阶段
单元测代码(看详细设计);
驱动模块:用来调用被测模块,桩模块:用来模拟被测模块所调用的子模块
- 驱动就是上级(主动调用),桩就是下级(被动顶替)。
- 自顶向下测,上级都是现成的,所以省驱动。
- 自底向上测,下级都是现成的,所以省打桩。
集成测接口(看概要设计);组装策略分为一次性组装和增量式组装
确认测需求(看能不能用);
系统测环境(看能不能跑)。
标准的软件测试顺序通常为:单元测试 → 集成测试(组装测试)→ 验收/有效性测试
6.2. 关于 Alpha vs Beta
-
Alpha (A):At developer's site(在开发者那),有人看着,环境单纯。
-
Beta (B):Bye-bye developer(开发者不在场),在用户那,环境复杂。
- 看到 “确认测试”、“验证用户需求” ➔ 选包含 用户参与、α测试、β测试、验收测试 的选项。
- 看到 “负载、压力、性能、可靠性、安装、容错” ➔ 一律归类为 系统测试。
6.3 白盒测试
也称为结构测试或逻辑驱动测试。它主要关注软件内部的逻辑结构和代码实现
-
语句覆盖 : 最基础的覆盖,仅要求每行代码至少被执行一次。
-
条件/判定覆盖 要求每个判断节点的“真”与“假”分支都至少被执行一次(判定覆盖不一定包含条件覆盖,条件覆盖也不一定包含判定覆盖,两者是互不包含的关系)。
-
条件组合覆盖 每个判定表达式中条件结果的所有可能组合至少出现一次。
-
修正的条件/判定覆盖 各个条件能够影响到包含的判定结果。
-
路径覆盖 : 要求覆盖程序中所有可能的执行路径组合。
我们假设一个生活场景:夜店安保的放行规则。
假设夜店大门的判定规则是:
如果 (是VIP卡 AND 满18岁) -> 允许进入这里有两个条件:A = 是VIP卡, B = 满18岁。判定结果:D = 允许进入。1. 条件/判定覆盖
它的性格: “差不多得了,都兼顾到就行。”
它的要求: 1. 每个条件(VIP卡、满18岁)的“真”和“假”都得出现一次。
2. 最终判定(允许进、不让进)的“真”和“假”也得出现一次。
选出的测试用例(只需 2 个):
用例1: (有VIP, 满18) -> 结果:进。(涵盖了 A=真, B=真, D=真)
用例2: (没VIP, 未满18) -> 结果:不进。(涵盖了 A=假, B=假, D=假)
致命缺陷: 看起来什么都测了,但如果保安是个糊涂蛋,他只看了VIP卡,根本没查年龄,这两个用例能发现保安的错误吗?发现不了!因为你把VIP和年龄同时变成了“假”,你不知道到底是哪个条件导致了“不让进”。它掩盖了逻辑漏洞。
2. 条件组合覆盖
它的性格: “暴力穷举,宁可错杀一千,不可放过一个。”
它的要求: 把所有条件的每一种可能组合,全部测一遍。
选出的测试用例(需要 4 个):
(有VIP, 满18) -> 进
(有VIP, 未满18) -> 不进
(没VIP, 满18) -> 不进
(没VIP, 未满18) -> 不进
致命缺陷: 逻辑最严密,但成本太高!如果有 10 个条件,那就是 $2^{10} = 1024$ 个用例。如果是 20 个条件,就是 100 万个用例。现实开发中根本测不起。
3. 修正的条件/判定覆盖 (MC/DC)
它的性格: “不仅要严谨,还要讲究性价比(控制变量法)。”
它的要求: 证明每一个条件都能“独立”影响最终结果。怎么证明?用控制变量法!固定其他条件不变,只改变其中一个条件,看结果变不变。
选出的测试用例(只需 3 个):
为了证明 VIP卡(A) 独立有用:保持年龄都是(满18),测一个(有VIP),测一个(没VIP)。 -> 需要用到 (有VIP, 满18) 和 (没VIP, 满18)。
为了证明 满18岁(B) 独立有用:保持都是(有VIP),测一个(满18),测一个(未满18)。 -> 需要用到 (有VIP, 满18) 和 (有VIP, 未满18)。
去重后,我们只需要这 3 个用例,就能像“组合覆盖”一样严谨地证明每个条件都起作用了,而且避免了指数级的用例爆炸。(注:航天/航空级别的软件强制要求达到 MC/DC 覆盖水平)。
从集合论的角度来看,路径覆盖通常包含了其他几种覆盖(即满足路径覆盖的测试用例集,通常也满足语句和判定覆盖),因此其测试强度和查错能力是最高的。
6.4 黑盒测试(功能测试)
| 方法名称 | 核心特征 |
| 等价类划分 | 分析输入条件时,我们需要同时确定有效等价类(正常的、合法的输入)和无效等价类(非正常的、不合法的输入)。在设计测试用例时,必须分别设计覆盖有效等价类和无效等价类的测试用例 |
| 边界值分析 | 专攻输入域的边界点 |
| 因果图法 |
从用自然语言书写的程序规格说明的描述中找出因(输入条件)和果(输出或程序状态的改变),可以通过因果图转换为判定表 |
| 判定表法 | 处理多条件的复杂逻辑组合 |
|
正交试验设计法 |
使用已经造好了的正交表格来安排试验并进行数据分析的一种方法,目的是用最少的测试用例达到最高的测试覆盖率 |
判定表驱动法
判定表是分析和表达多逻辑条件下执行不同操作情况的工具。它能够将复杂的逻辑关系和多条件组合情况清晰地表达出来。
适用场景:
当规格说明书中包含多个逻辑条件。
这些条件之间存在组合关系(如:“如果 A 且 B,则执行 X”)。
不同的条件组合对应不同的动作(Action)。
需要检查条件之间的依赖关系或矛盾。
判定表的组成:
条件桩:列出问题的所有条件(输入)。
动作桩:列出问题规定的可能采取的操作(输出)。
条件项 :列出针对它左列条件的取值(真/假)。
动作项 :列出在条件项的各种取值情况下应该采取的动作。
6.5 回归测试
回归测试是指修改了旧代码后,重新进行测试以确认修改没有引入新的错误或导致其他代码产生错误
验证变更 :确认修改的 Bug 已修复,或新功能已正确实现
防退化 :确保软件原有的、正确的功能没有被破坏。
6.6 静态测试
指被测试程序不在机器上运行,而采用人工监测和计算机辅助分析的手段对程序进行监测
静态分析主要包含以下两个层面
- 对文档的静态测试
- 对代码的静态测试
静态分析的核心维度(极高频考点)
- 看到关键词“未定义、赋值、引用、初始化” ➔ 选 数据流分析。
- 看到关键词“死代码、无法达到的语句、未调用” ➔ 选 控制流分析。
- 看到关键词“参数数量/顺序/类型不匹配/子程序声明、一致性、形参/实参” ➔ 选 接口分析。
- 看到关键词“数组越界、除数为0、括号不配对” ➔ 选 表达式分析。
- 看到 “输入/输出变量、依赖关系” ➔ 选 信息流分析
- 看到 “所有可能的路径” ➔ 选 路径分析
6.7. BRO 测试策略
BRO 测试的主要目的是发现条件表达式中 布尔变量 和 关系操作符如 >,<,=,≥,≤>,<,=,≥,≤)的错误。
为了检测一个关系操作符(例如 E1>E2)是否正确,我们需要测试三个维度的约束,以防止开发人员误写了操作符(比如把 > 写成了 ≥ 或者 ≠):
-
大于 (>):使得差值为正。
-
等于 (=):使得差值为零(边界测试)。
-
小于 (<):使得差值为负。
6.7.1.逻辑推导过程
题目中的条件是 𝐶1:(𝐸1>𝐸2) & (𝐸3<𝐸4)。
这是一个逻辑 “与” (&) 表达式。为了充分测试这个组合条件,BRO 策略要求我们分别测试每一个子条件,同时让另一个子条件保持为“真” (True),以便让被测子条件的错误能传播到整个表达式的结果中。
根据 BRO 测试策略,要检查逻辑表达式 𝐶1:(𝐸1>𝐸2) & (𝐸3<𝐸4)中的关系操作符错误,必须满足以下条件集:
-
{(>, <)}:基础测试,两个条件都为真。
-
{(=, <), (<, <)}:保持第二个条件为真,测试第一个条件的边界和失效情况。
-
{(>, =), (>, >)}:保持第一个条件为真,测试第二个条件的边界和失效情况。
组合在一起即为 Option A:{(>,=),(>,>),(>,<),(<,<),(=,<)}。
6.7.2. 知识点总结
| 概念 | 说明 |
| BRO 策略 | Branch and Relational Operator Testing,用于发现分支与关系运算符错误。 |
| 测试核心 | 对于关系表达式,必须覆盖 大于、等于、小于 三种情况。 |
| 逻辑与 (&) | 测试子项 A 时,必须保证子项 B 为 True,反之亦然。 |
6.8 自动化测试脚本
线性脚本:录制手工测试得到的脚本 。
数据驱动脚本:测试输入存储在独立数据文件中 。
共享脚本:一个脚本可被多个用例使用。
6.9 测试和调试
①测试的目的是找出存在的错误,而调试的目的是定位错误并修改程序以修正错误;
②调试是测试之后的活动,测试和调试在目标、方法和思路上都有所不同;
③测试从一个已知的条件开始,使用预先定义的过程,有预知的结果;调试从一个未知的条件开始,结束的过程不可预计;
④测试过程可以实现设计,进度可以实现确定;而调试不能描述过程或持续时间。
7. UML 2.0
在UML 2.0中,为了处理复杂的逻辑交互,如循环、选择、并行 等结构,不再单纯使用简单的线条,而是使用“组合片段”或称为“序列片段”来表示。
消息类型 :对象之间的交互通过消息传递。UML 2.0 定义的标准消息类型包括:
参与者销毁消息: 销毁一个对象实例。
参与者创建消息 : 创建一个新的对象实例。
返回消息: 从过程调用返回(虚线箭头)。
异步消息: 发送后不需等待(开放箭头)。
同步消息: 发送后需等待响应(实心三角箭头)。
8. 软件开发
软件开发过程:主要活动包括软件描述、开发、有效性验证和演化 。
软件设计活动:包括数据设计、软件结构设计、人机界面设计和过程设计 。
9. 软件复用
1. 复用的对象(复用什么?)
不仅是代码复用,考试中必须明确,复用贯穿整个软件过程:
- 包含: 需求分析文档、设计文档、程序代码、测试用例、领域知识。
2. 复用的维度分类(极高频考点!)
按照重用活动是否跨越应用领域,历年考试极其喜欢考查以下两个概念的区分:
- 横向重用:
- 特征: 重用不同应用领域中的软件元素,通用性极强。
- 典型例子: 数据结构、分类算法、人机界面构件等。考试中常考的结论是:标准函数库是一种典型的、原始的横向重用机制。
- 纵向重用:
- 特征: 在一类具有较多公共性的应用领域之间(即同行业/同领域内部)进行软部件重用。
- 核心关键点: 纵向重用的主要关键点是领域分析,即根据应用领域的特征及相似性预测软部件的可重用性。
3. 复用的时机与模式
(注:2023年真题曾直接考查填空:“软件架构复用包括机会复用和系统复用”。)
在架构评估和系统设计中,按规划的主被动程度划分:
- 机会复用(资产复用): 偏被动/随机。开发过程中遇到问题了,才去翻看有没有现成的构件可以“拿来主义”。
- 系统复用(计划复用): 偏主动/系统性。在开发之前(如架构设计阶段)就进行严密规划,明确界定哪些模块复用现有资产,哪些必须新开发。
4. 复用的标准流程
基于构件的软件开发,其复用过程标准流程顺序为:
- 构造/获取(获取构件): 解决“东西从哪来”。常见方法包括:修改已有构件、通过遗留工程提取、购买现成的商用构件(COTS)、全新开发。
- 管理(建立构件库): 解决“东西怎么存”。将构件进行分类、打标签、入库,方便后续的检索和复用。
- 使用(组装与集成): 解决“东西怎么用”。在实际项目中检索出相应的构件,进行适应性修改、配置和组装。
🧠 考场秒杀口诀:
- 考元素: 选需求、设计、代码、测试、领域知识(看到“项目计划/范围”直接排除)。
- 考维度: 看到“不同领域/标准函数库”选横向;看到“同一领域/领域分析”选纵向。
- 考时机: 看到“被动/随机”选机会复用;看到“主动/提前规划”选系统复用。
10. 构件相关
构件的定义
构件是一个独立分发和部署的单元,它通过接口对外提供服务。
在软考中遇到“构件 vs 对象”的题目,记住核心差异:
- 对象是代码级的、动态的、有状态和唯一标识的;
- 构件是架构/部署级的、通常是静态的代码集合、状态往往由外部“容器”(Docker,Tomcat)接管,且通过“接口”对外提供服务,支持动态发现。
构件的三个特性
自包含与独立性:构件必须能独立部署,它与其运行环境和其他构件是完全分离的。
不可拆分的独立部署单元:构件作为一个整体被安装,不能拆开来用。
强制要求黑盒,外部看不见内部是如何存储状态的,但构件本身依然拥有状态。
构件的分类
适应性构件:指经过修改或配置以适应新环境的构件。
装配性构件:指用于胶合不同构件的“胶水代码”或中间件。
基于构件的开发模型
基于构件的开发模型由软件的需求分析定义、体系结构设计、构件库建立、应用软件构建以及测试和发布5个阶段组成。
主流构件标准模型辨析(必考!)
考试极爱考查CORBA、J2EE(EJB)和COM这三种主流构件标准内部的角色和作用:
- CORBA模型: 记住**伺服对象Servant**是最终完成客户请求的服务对象实现;**可移植对象适配器(POA)**的作用是在底层传输平台与接收调用并返回结果的对象实现之间进行协调。
- EJB (J2EE)模型: 记住**会话型构件**负责完成服务端与客户端的交互;**实体型构件**用于数据持久化;**消息驱动构件**用来处理并发和异步访问操作。
- COM对象组装: 支持包含(外部对象把请求“转发”给内部对象)和聚集(直接把内部对象的接口引用传给外部,不转发)两种重用形式。
| 特性 | 包含 | 聚集 |
| 形象比喻 | 转发 | 直通 |
| 客户可见性 | 客户不知道内部对象的存在。 | 客户可以直接看到内部对象的接口。 |
| 调用方式 | 客户调用外部对象 -> 外部对象转发给内部对象。 | 客户获得内部对象的接口指针 -> 直接调用内部对象。 |
| 实现难度 | 简单(单纯的函数调用转发)。 | 复杂(需要处理 IUnknown 的委托,防止引用计数混乱)。 |
| 性能 | 略低(多了一次转发调用的开销)。 | 高(直接调用,无中间商赚差价)。 |
构件失配问题(常考分类)
想象一下,你正在用乐高积木拼一个超级复杂的模型,但这些积木不是同一家公司生产的,有些是乐高原厂的,有些是国产兼容品牌的,有些甚至是木头做的。你把它们往一起拼的时候,肯定会遇到各种对不上的情况。在软件架构里,这就叫“失配”
历年考试常要求考生区分失配的种类:
- 构件失配: 由于系统对构件基础设施、控制模型和数据模型的假设存在冲突引起(构件自己心里想的那个“世界观”,和系统实际给它的“环境”不一样)。
- 连接子失配: 由于系统对构件交互协议、构件连接时数据格式的假设存在冲突引起。(两个构件本身的底子可能没问题,但它们两个要互相传东西的时候,那个“接口”或者“沟通方式”卡住了。)
11. 用例、类、构件内部关系辨析
11.1、 用例之间的关系
用例图主要描述系统的功能需求。在软考中,用例之间的标准关系只有三种,主要目的是把公共信息抽取出来以便复用:
- 包含关系
- 考点特征:当可以从两个或两个以上的用例中提取公共行为时使用。
- 秒杀词:提取公共行为、必然执行、基础用例必定调用它。
- 图中《include》
- 扩展关系
- 考点特征:如果一个用例混合了两种以上的场景,根据情况可能发生多种分支,则将特定条件触发的行为作为扩展用例。
- 秒杀词:特定条件触发、分离不同行为、可能发生也可能不发生。
- 图中《extend》
- 泛化关系
- 考点特征:多个用例共同拥有类似结构和行为,将共性抽象成为父用例,子用例是父用例的特殊形式(相当于继承)。
- 秒杀词:抽象成父用例、特殊/一般关系。
- generalization 图中空心箭头
11.2 类图中的关系
类图描述系统的代码级静态结构。类与类之间的标准关系共有 六种:
- 泛化关系:描述特殊与一般的关系(即面向对象中的继承),带有空心三角形箭头的实线,箭头指向父类
- 实现关系 :接口与实现该接口的类之间的关系。
- 依赖关系 :一个事物发生变化会影响另一个事物(通常是局部变量或方法参数),带有普通箭头的虚线,箭头指向被依赖的类
- 关联关系:描述了一组链,链是对象之间的连接(通常是成员变量)。
- 聚合关系:描述整体与部分的关系,且整体与部分生命周期不同(可以分开,例如学校和学生),带空心菱形的实线。
- 组合关系 :描述整体与部分的关系,且整体与部分生命周期相同(不可分开,例如学校和院系)。

- 关于“包含”:
- 在用例中,叫
Include(提取一定会执行的公共行为)。- 在构件重用中,叫
Containment(外部对象把请求转发给内部对象)。- 类图中没有“包含”关系!
- 关于“聚集/聚合”:
- 在类图中,翻译为
Aggregation(表示整体与部分,生命周期不同)。- 在构件重用中,也叫
Aggregation(直接暴露接口,不转发请求)。- 用例图中没有“聚集”关系!如果考用例关系出现“聚集”,直接打叉!
- 关于“泛化”:
- 在用例和类图中都有,意思都是“抽出共性,形成父子继承关系”。
- COM构件没有泛化(不支持继承)!
12. 面向对象设计原则
| 原则名称 | 官方定义 | 核心逻辑锚点与大白话 |
|---|---|---|
| 开闭原则 (OCP) | 软件实体应当对扩展开放,对修改关闭。 | “加新功能,不改老代码”。 架构的理想终极目标。 |
| 依赖倒置原则 (DIP) | 抽象不应该依赖于细节,细节应当依赖于抽象。要针对接口编程。 | “只认插座,不认插头”。 达成开闭原则的主要机制。高层定义接口,底层实现接口。 |
| 里氏替换原则 (LSP) | 所有引用基类(父类)的地方必须能透明地使用其子类的对象。 | “无缝顶岗,挂羊头绝不卖狗肉”。 达成开闭原则的重要规范。子类可以扩展新功能,但绝不能改变父类原有的行为和规则。 |
对于违反里氏替换原则的两个类A和B,可以采用的候选解决方案中,正确的是( ).
A.尽量将一些需要扩展的类或者存在变化的类设计为抽象类或者接口,并将其作为基类,在程序中尽量使用基类对象进行编程
B.创建一个新的抽象类C,作为两个具体类的超类,将A和B共同的行为移动到C中,从而解决A和B行为不完全一致的问题
C.将B到A的继承关系改成组合关系
D.区分是“Is-a”还是“Has-a”。如果是Is-a,可以使用继承关系,如果是Has-a,应该改成组合或聚合关系
它的正确答案通常是 B(或者在某些多选题里 B 和 C 都算对,但在单选的经典题库中,B 是标准答案)。
1. 什么是“里氏替换原则 (LSP)”?
大白话定义: 儿子必须能完美替代老子,且系统不出错(不能“坑爹”)。 也就是说,在代码里,任何需要用到父类(A)的地方,我把子类(B)传进去,程序必须照样跑,行为结果必须符合预期。
经典的违背例子(坑爹现场):
父类 A 是“鸟(Bird)”,里面有个方法叫
fly()(飞)。子类 B 是“鸵鸟(Ostrich)”。从生物学上讲,鸵鸟是鸟,所以 B 继承了 A。
出问题了: 程序里有个功能是“让所有的鸟起飞”。当你把鸵鸟传进去,调用
fly()的时候,鸵鸟飞不起来,只能抛出异常或者原地打转。这就破坏了程序原本对“鸟”的预期。—— 这就是 B 违反了 A 的里氏替换原则。2. 怎么解决这个“坑爹”问题?
既然“鸵鸟”直接继承“鸟(会飞的鸟)”会出问题,我们该怎么改代码?
正确选项 B 的思路(找个共同的长辈):
做法: 既然 A(鸟,假设默认会飞)和 B(鸵鸟)不能是父子关系,那我们新建一个抽象的爷爷类 C(比如叫
Animal或者BaseBird)。把 A 和 B 共同的行为(比如吃东西、睡觉)放到 C 里面。
然后让 A(会飞的鸟)继承 C,并加上
fly();让 B(鸵鸟)也继承 C,加上run()。结果: A 和 B 变成了兄弟关系,不再是父子关系。以后程序只需要调用安全的长辈类 C(只会要求吃饭睡觉,不要求飞),完美解决了冲突!
这就是选项 B 的意思:创建一个新的抽象类 C,作为两者的超类。
选项 C 的思路(解除父子关系,改为雇佣关系):
做法: 将 B 到 A 的继承关系,改成组合关系。
例子: 假设 A 是
ArrayList(数组列表,可以随便插队),B 是Stack(栈,只能后进先出)。以前 Java 把Stack设计成继承ArrayList,导致有人拿Stack也能随便插队,违反了栈的原则(违反 LSP)。解决:
Stack不当ArrayList的儿子了,而是内部包含一个ArrayList来帮自己存数据,这叫“组合”。对外依然只提供正常的出栈/入栈方法。注:C 也是一种解决 LSP 违规的有效手段(多用组合,少用继承),但在题库的标准单选中,B 是最针对“提取共性”的标准重构手法。
为什么 A 和 D 不是直接的解决方案?
选项 A: “尽量将类设计为抽象类或接口,使用基类编程”。这说的是依赖倒置原则(DIP)和开闭原则(OCP)。它是教你怎么搭框架,而不是教你怎么解决 A 和 B 已经产生的具体冲突。
选项 D: “区分 Is-a 和 Has-a”。这是一条通用的设计经验法则(判断该用继承还是组合),是在你写代码之前用来预防问题的,而不是在 A 和 B 已经违反了原则后,直接拿来做代码重构的“具体手术方案”。
在面向对象设计中,边界类可以实现界面控制、外部接口和环境隔离。控制类 作为完成用例业务的责任承担者,协调、控制其他类共同完成用例规定的功能或行为。实体类是用于对必须存储的信息和相关行为建模的类,它直接映射了需求中的每个业务实体
13. 软件系统工具
通常可以按照软件过程活动将软件工具分为软件开发工具、软件维护工具、软件管理工具和软件支持工具
14. 逆向工程和再工程
- 逆向工程:从已有软件系统出发,把代码、数据结构、模块关系等低层实现,抽取为更高层次的抽象表示,例如设计、体系结构、数据模型。
- 再工程:在逆向分析得到的信息基础上,对现有系统进行修改、优化、重构,并产出新版本。
逆向工程导出的信息可以分为实现级、结构级、功能级和领域级四个抽象层次。程序的抽象语法树属于(29);反映程序分量之间相互依赖关系的信息属于(30)。
(29)A.实现级 B.结构级 C.功能级 D.领域级
(30)A.实现级 B.结构级 C.功能级 D.领域级
软考官方教程对逆向工程 4 个抽象层次的标准原话定义如下:
- 实现级:包括程序的抽象语法树、符号表等信息。
- 结构级:包括反映程序分量之间相互依赖关系的信息,例如调用图、结构图等。
- 功能级:包括反映程序段功能及程序段之间关系的信息。
- 领域级:包括反映程序分量或程序诸实体与应用领域概念之间对应关系的信息。
逆向工程恢复信息的方法还有以下几种:
变换式方法用于导出实现级、结构级、功能级。
基于领域知识的方法用于导出功能级、领域级。
看到 “语法树 (AST)、符号表、变量” 选 实现级
看到 “依赖关系、调用图、组件”选 结构级
看到 “数据流、控制流、做某事”选 功能级 (“程序段之间关系” = “数据流、控制流”:在功能层面上,两段程序怎么发生关系?必然是通过数据流(你计算完的数据传给我)或者控制流)
看到 “概念模型、实体关系 (ER)、领域业务” 选 领域级
15. 移植工作
1、计划阶段,在计划阶段,要进行现有系统的调查整理,从移植技术、系统内容(是否进行系统提炼等)、系统运行三个方面,探讨如何转换成新系统,决定移植方法,确立移植工作体制及移植日程。
2、准备阶段,在准备阶段要进行移植方面的研究,准备转换所需的资料。该阶段的作业质量将对以后的生产效率产生很大的影响。
3、转换阶段,这一阶段是将程序设计和数据转换成新机器能根据需要工作的阶段。提高转换工作的精度,减轻下一阶段的测试负担是提高移植工作效率的基本内容。
4、测试阶段,这一阶段是进行程序单元、工作单元测试的阶段。在本阶段要核实程序能否在新系统中准确地工作。所以,当有不能准确工作的程序时,就要回到转换阶段重新工作。
5、验证阶段,这是测试完的程序使新系统工作,最后核实系统,准备正式运行的阶段。
16. 快速应用开发
1.(Rapid Application Development,RAD)通过使用基于构件的开发方法获得快速开发。当系统模块化程度较高时,最适合于采用RAD方法。
2.这句话的内在逻辑是:目标是“快”(RAD) 手段是“拼装现成零件”(基于构件) 前提条件是“系统必须能被合理拆解成独立的部分”(模块化程度高)。
17. 软件开发环境(SDE)的集成机制
根据功能的不同,开发环境的集成机制主要划分为以下三个核心部分:
- 环境信息库(对应数据集成): 它是软件开发环境的核心,主要用来存储与系统开发相关的各类信息(如分析设计文档、代码、测试报告、模板、可复用构件等),并支持整个开发过程中的信息交流与共享。
- 过程控制与消息服务器(对应控制/过程集成): 它是实现过程集成和控制集成的基础。主要负责按照软件开发过程的要求进行工具的选择与组合,并使各个开发工具之间能够进行并行通信和协同工作。
- 环境用户界面(对应界面集成): 统一的、具有一致性的用户界面是软件开发环境的重要特征。它能为用户提供统一的操作方式,减轻开发人员的学习负担
18. 模式的三种层次
模式的三种层次划分(由高到低):架构模式、设计模式、惯用法。弄清它们在抽象粒度和语言相关性上的区别是解题关键。
- 1. 架构模式—— 高层宏观决策
- 核心特征: 反映了开发软件系统过程中所作的基本设计决策,是最高层次的模式。
- 具体表现: 它定义了系统的总体组织结构框架。例如经典的 C/S结构、MVC、管道-过滤器等都属于架构模式。
- 2. 设计模式—— 中层局部细化
- 核心特征: 主要关注软件系统的具体设计,描述了如何细化系统的各个子系统或构件,以及它们之间的协同关系。
- 最重要特点: 它与具体的实现语言无关(独立于实际编程语言),无论是 Java、C++ 还是 C#,都可以使用同一套设计模式(如工厂模式、单例模式、观察者模式等)。
- 3. 惯用法—— 底层代码实现
- 核心特征: 是最低层的模式,直接关注软件系统的设计与实现,描述了如何实现构件及构件之间的关系。
- 最重要特点: 惯用法是与某种特定的程序设计语言密切相关的。例如题干中提到的“引用-计数 ”,就是专门在 C++ 语言中管理动态资源时特有的一种惯用法。
19. 过程能力成熟度模型(CMM)
- 过程能力成熟度模型(CMM)在软件开发机构中被广泛用来指 导软件过程改进。该模型描述了软件成立能力的 5个成熟级别,每一级都包含若干关键过程 域(Key Process.Areas,KPA)。
- CMM的第二级为可重复级,它包括 6个关键过程域,分别是:需求管理、软件项目计 划、软件项目跟踪和监督、软件分包合同管理、软件质量保证和软件配置管理。
- 需求管理的目标是为软件需求建立一个基线,提供给软件工程和管理使用;软件计划、 产品和活动与软件需求保持一致。
20. 软件产品线过程模型
主要有双生命周期模型、SEI 模型和三生命周期模型。双生命周期模型分成两个重叠的生命周期,分别是领域工程和应用工程。
21. 软件质量模型
- 软件质量模型中的三维度模型(McCall 模型),它从用户角度划分软件质量的三个主要方面:
- 产品运行 :强调软件在运行时的质量特性,如正确性、可靠性、效率、完整性等。
- 产品修改 :关注软件维护和修改的难易程度,如可维护性、灵活性、测试性。
- 产品转移 :强调软件在不同平台和环境中的适应能力,如可移植性、可重用性、互操作性
AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。
更多推荐



所有评论(0)