软件设计师_第十章:软件工程(上)
目录
CMM模型(背❤)
CMMI模型(记❤)
瀑布模型
增量模型
演化模型
原型模型
螺旋模型
喷泉模型
统一过程(UP)模型(记❤)
敏捷方法
极限编程(记❤)
水晶法(Crystal)
并列争求法(Scrum)
自适应软件开发(ASD)
敏捷统一过程(AUP)
软件需求(记❤)
系统设计
一 概要设计
二 详细设计
系统测试
测试分类
单元测试
集成测试
黑盒测试
McCabe度量法
白盒测试
伪代码+白盒测试+McCabe度量法
CMM模型(背❤)
初始级 ( Initial ) | 软件过程的特点是杂乱无章,有时甚至很混乱,几乎没有明确定义的步骤,项目的成功完全依赖个人的努力和英雄式核心人物的作用。 |
可重复级 ( Repeatable) | 建立了基本的项目管理过程和实践来跟踪项目费用、进度和功能特性,有必要的过程准则来重复以前在同类项目中的成功。 |
已定义级 (Defined) | 管理和工程两方面的软件过程已经文档化、标准化,并综合成整个软件开发组织的标准软件过程。所有项目都采用根据实际情况修改后得到的标准软件过程来开发和维护软件。 |
已管理级 (Managed ) | 制定了软件过程和产品质量的详细度量标准。软件过程的产品质量都被开发组织的成员所理解和控制。 |
优化级 (Optimized) | 加强了定量分析,通过来自过程质量反馈和来自新观念、新技术的反馈使过程能不断持续地改进。 |
CMMI模型(记❤)
阶段式模型
阶段式模型的结构类似于CMM,它关注组织的成熟度。CMMI-SE/SW/IPPD 1.1版中有5个成熟度等级。
- 初始的:过程不可预测且缺乏控制。
- 已管理的:过程为项目服务。
- 已定义的:过程为组织服务。
- 定量管理的:过程已度量和控制。
- 优化的:集中于过程改进
连续式模型
CL0 (未完成的) | 过程域未执行或未得到CL1中定义的所有目标。 指未执行过程,表明过程域的一个或多个特定目标没有被满足 |
CL1(已执行的) | 其共性目标是过程将可标识的输入工作产品转换成可标识的输出工作产品,以实现支持过程域的特定目标。 指过程通过转化可识别的输入工作产品,产生可识别的输出工作产品,关注于过程域的特定目标的完成 |
CL2 (已管理的) | 其共性目标集中于已管理的过程的制度化。根据组织级政策规定过程的运作将使用哪个过程,项目遵循己文档化的计划和过程描述,所有正在工作的人都有权使用足够的资源,所有工作任务和工作产品都被监控、控制和评审。 过程作为己管理的过程制度化,针对单个过程实例的能力 |
CL3 (已定义级的) | 其共性目标集中于已定义的过程的制度化。过程是按照组织的剪裁指南从组织的标准过程集中剪裁得到的,还必须收集过程资产和过程的度量,并用于将来对过程的改进。 过程作为已定义的过程制度化,关注过程的组织级标准化和部署 |
CL4(定量管理的) | 其共性目标集中于可定量管理的过程的制度化。使用测量和质量保证来控制和改进过程域,建立和使用关于质量和过程执行的定量目标作为管理准则。 过程作为定量管理的过程制度化 |
CL5 (优化的) | 使用量化(统计学)手段改变和优化过程域,以满足客户要求的改变和持续改进计划中的过程域的功效。 |
瀑布模型
说明:
线性顺序,以文档作为驱动,项目的阶段评审和文档控制为手段对开发过程作为指导
适用于软件需求明确的软件项目的模型
优点:
容易理解,管理成本低
缺点:
需要用户明确表达需求,后期测试工作巨大,问题在后期才能显现和爆发
客户参与度低,可能导致最终产品与客户需求有较大区别
增量模型
增量模型融合了瀑布模型的基本成分和原型实现的迭代特征,它假设可以将需求分段为一系列增量产品,每一增量可以分别开发。当使用增量模型时,第1个增量往往是核心的产品。客户对每个增量的使用和评估都作为下一个增量发布的新特征和功能,这个过程在每一个增量发布后不断重复,直到产生了最终的完善产品。增量模型强调每一个增量均发布一个可操作的产品。
优点:
瀑布模型的全部优点,第一版的增量产品开发时间短,风险小,与用户沟通频繁,快速构造可运行产品
缺点:
如果没有对用户的变更要求进行规划,会初始增量会导致后来的增量产品的不稳定,并且开发复杂,组织复杂,管理发生的成本、进度和配置的复杂性可能会超出组织的能力。
演化模型
原型模型
适用场景:
客户不能表达全面的需求,模糊不清,经常变化
有了快速原型模型
系统规模不太大,不太复杂
优点:
快速开发出一个原型,和用户沟通
得到反馈意见有进行下一轮的对原型的改进
螺旋模型
说明:
特有的对于规模很大的项目,有风险分析,对于瀑布模型和演化模型的结合
特点:
适合大又复杂的项目
支持用户的需求动态变化
降低软件开发风险
在使用螺旋模型进行软件开发时,需要开发人员具有相当丰富的风险评估经验和专门知识。另外,过多的迭代次数会增加开发成本,延迟提交时间。
喷泉模型
说明:
用户需求为动力,对象为驱动,适合面向对象开发
允许各个开发活动交叉迭代进行,没有明显的界线,节省效率和时间
它克服了瀑布模型不支持软件重用和多项开发活动集成的局限性。喷泉模型使开发过程具有迭代性和无间隙性
统一过程(UP)模型(记❤)
统一过程模型是一种 “用例和风险驱动,以架构为中心,迭代并且增量” 的开发过程,由UML方法和工具支持。迭代的意思是将整个软件开发项目划分为许多个小的 “袖珍项目”,每个 “袖珍项目” 都包含正常软件项目的所有元素:计划、分析和设计、构造、集成和测试,以及内部和外部发布。
起始阶段 (Inception Phase) | 起始阶段专注于项目的初创活动,产生的主要工作产品有构想文档(Vision Document)、初始用例模型、初始项目术语表、初始业务用例、初始风险评估、项目计划(阶段及迭代)、业务模型以及一个或多个原型(需要时)。 |
精化阶段 (Elaboration Phase ) | 精化阶段在理解了最初的领域范围之后进行需求分析和架构演进,产生的主要工作产品有用例模型、补充需求(包括非功能需求)、分析模型、软件体系结构描述、可执行的软件体系结构原型、初步的设计模型、修订的风险列表、项目计划(包括迭代计划、调整的工作流、里程碑和技术工作产品)以及初始用户手册。 |
构建阶段 (Construction Phase ) | 构建阶段关注系统的构建,产生实现模型,产生的主要工作产品有设计模型、软件构件、集成的软件增量、测试计划及步骤、测试用例以及支持文档(用户手册、安装手册和对于并发增量的描述)。. |
移交阶段(Transition Phase) | 移交阶段关注于软件提交方面的工作,产生软件增量,产生的主要工作产品有提交的软件增量、β测试报告和综合用户反馈。 |
在每个迭代中有5个核心工作流:捕获系统应该做什么的需求工作流,精化和结构化需求的分析工作流,在系统构架内实现需求的设计工作流,构造软件的实现工作流,验证实现是否如期望那样工作的测试工作流。随着UP的阶段进展,每个核心工作流的工作量发生了变化。4个技术阶段由主要里程碑所终止。
- 初始阶段:生命周期目标。
- 精化阶段:生命周期架构。
- 构建阶段:初始运作功能。
- 移交阶段:产品发布。
统一过程的典型代表是RUP (Rational Unified Process)。RUP是UP的商业扩展,完全兼容UP,但比UP更完整、更详细。
敏捷方法
极限编程(记❤)
XP是一种轻量级(敏捷)、高效、低风险、柔性、可预测的、科学的软件开发方式。它由价值观、原则、实践和行为4个部分组成,彼此相互依赖、关联,并通过行为贯穿于整个生存周期。
4大价值观 | 沟通、简单性、反馈和勇气 |
5个原则 | 快速反馈、简单性假设、逐步修改、提倡更改和优质工作。 |
12个最佳实践 | 计划游戏(快速制定计划、随着细节的不断变化而完善) 小型发布(系统的设计要能够尽可能早地交付) 隐喻(找到合适的比喻传达信息) 简单设计(只处理当前的需求,使设计保持简单) 测试先行(先写测试代码,然后再编写程序) 重构(重新审视需求和设计,重新明确地描述它们以符合新的和现有的需求) 结对编程 集体代码所有制 持续集成(可以按日甚至按小时为客户提供可运行的版本) 每周工作40个小时 现场客户 编码标准。 |
水晶法(Crystal)
水晶法认为每一个不同的项目都需要一套不同的策略、 约定和方法论,认为人对软件质量有重要的影响,因此随着项目质量和开发人员素质的提高,项目和过程的质量也随之提高。通过更好地交流和经常性的交付,软件生产力得到提高。
并列争求法(Scrum)
并列争求法使用迭代的方法,其中,把每30天一次的迭代称为一个“冲刺”,并按需求的优先级别来实现产品。多个自组织和自治的小组并行地递增实现产品。协调是通过简短的日常情况会议来进行,就像橄榄球中的“并列争球”
自适应软件开发(ASD)
ASD有6个基本的原则:
- 有一个使命作为指导;
- 特征被视为客户价值的关键点;
- 过程中的等待是很重要的,因此“重做”与“做”同样关键;
- 变化不被视为改正,而是被视为对软件开发实际情况的调整;
- 确定的交付时间迫使开发人员认真考虑每一个生产的版本的关键需求;
- 风险也包含其中。
敏捷统一过程(AUP)
敏捷统一过程(Agile Unifed Process, AUP) 采用 “在大型上连续 ”以及在 “在小型上迭代” 的原理来构建软件系统。采用经典的UP 阶段性活动(初始、精化、构建和转换),提供了一系列活动,能够使团队为软件项目构想出一个全面的过程流。在每个活动里,一个团队迭代使用敏捷,并将有意义的软件增量尽可能快地交付给最终用户。每个AUP迭代执行以下活动:
- 建模。建立对商业和问题域的模型表述,这些模型 “足够好” 即可,以便团队继续前进。
- 实现。将模型翻译成源代码。
- 测试。像XP一样,团队设计和执行一系列的测试来发现错误以保证源代码满足需求。
- 部署。对软件增量的交付以及获取最终用户的反馈。
- 配置及项目管理。着眼于变更管理、风险管理以及对团队的任一制品的控制。项目管理追踪和控制开发团队的工作进展并协调团队活动。
- 环境管理。协调标准、工具以及适用于开发团队的支持技术等过程基础设施。
软件需求(记❤)
- 功能需求。考虑系统要做什么,在何时做,在何时以及如何修改或升级。
- 性能需求。考虑软件开发的技术性指标。例如,存储容量限制、执行速度、响应时间及吞吐量。
- 用户或人的因素。考虑用户的类型。例如,各种用户对使用计算机的熟练程度,需要接受的训练,用户理解、使用系统的难度,用户错误操作系统的可能性等。
- 环境需求。考虑未来软件应用的环境,包括硬件和软件。对硬件设备的需求包括机型、外设、接口、地点、分布、湿度、磁场干扰等;对软件的需求包括操作系统、网络、数据库等。
- 界面需求。考虑来自其他系统的输入,到其他系统的输出,对数据格式的特殊规定, 对数据存储介质的规定。
- 文档需求。考虑需要哪些文档,文档针对哪些读者。
- 数据需求。考虑输入、输出数据的格式,接收、发送数据的频率,数据的准确性和精度,数据流量,数据需保持的时间。
- 资源使用需求。考虑软件运行时所需要的数据、其他软件、内存空间等资源;软件开发、维护所需的人力、支撑软件、开发设备等。
- 安全保密要求。考虑是否需要对访问系统或系统信息加以控制,隔离用户数据的方法,用户程序如何与其他程序和操作系统隔离以及系统备份要求等。
- 可靠性要求。考虑系统的可靠性要求,系统是否必须检测和隔离错误;出错后,重启系统允许的时间等。
- 软件成本消耗与开发进度需求。考虑开发是否有规定的时间表,软/硬件投资有无限制等。
- 其他非功能性要求。如采用某种开发模式,确定质量控制标准、里程碑和评审、验收标准、各种质量要求的优先级等,以及可维护性方面的要求。
系统设计
一 概要设计
1 设计软件系统总体结构
其基本任务是采用某种设计方法,将一个复杂的系统按功能划分成模块;确定每个模块的功能;确定模块之间的调用关系;确定模块之间的接口,即模块之间传递的信息;评价模块结构的质量。
软件系统总体结构的设计是概要设计关键的一步,直接影响到下一个阶段详细设计与编码的工作。软件系统的质量及一些整体特性都在软件系统总体结构的设计中决定。
2 数据结构及数据库设计
数据结构的设计
逐步细化的方法也适用于数据结构的设计。在需求分析阶段,已经通过数据字典对数据的组成、操作约束和数据之间的关系等方面进行了描述,确定了数据的结构特性,在概要设计阶段要加以细化,详细设计阶段则规定具体的实现细节。在概要设计阶段,宜使用抽象的数据类型。
数据库的设计
数据库的设计是指数据存储文件的设计,主要进行以下几方面设计。
- 概念设计。在数据分析的基础上,采用自底向上的方法从用户角度进行视图设计,一般用E-R模型来表述数据模型。E-R模型既是设计数据库的基础,也是设计数据结构的基础。
- 逻辑设计。E-R 模型是独立于数据库管理系统(DBMS)的,要结合具体的DBMS特征来建立数据库的逻辑结构。
- 物理设计。对于不同的DBMS,物理环境不同,提供的存储结构与存取方法各不相同。物理设计就是设计数据模式的一些物理细节,如数据项存储要求、存取方法和索引的建立等。本节对数据库技术不做详细讨论,详细内容参见本书第7章。
3 编写概要设计文档
文档主要有概要设计说明书、数据库设计说明书、用户手册以及修订测试计划。
4 评审
对设计部分是否完整地实现了需求中规定的功能、性能等要求,设计方法的可行性,关键
的处理及内外部接口定义的正确性、有效性、各部分之间的一致性等都 一 一进行评审。
二 详细设计
- 对每个模块进行详细的算法设计,用某种图形、表格和语言等工具将每个模块处理过程的详细算法描述出来。
- 对模块内的数据结构进行设计。
- 对数据库进行物理设计,即确定数据库的物理结构。
- 其他设计。根据软件系统的类型,还可能要进行以下设计。
-
- ① 代码设计。为了提高数据的输入、分类、存储和检索等操作,节约内存空间,对数据库中某些数据项的值要进行代码设计。
- ② 输入/输出格式设计。
- ③ 用户界面设计。
- 编写详细设计说明书。
- 评审。对处理过程的算法和数据库的物理结构都要评审。系统设计的结果是一系列的系统设计文件,这些文件是物理实现一个信息系统(包括硬件设备和编制软件程序)的重要基础。
系统测试
意义
系统测试是为了发现错误而执行程序的过程,成功的测试是发现了至今尚未发现的错误的测试。
目的
测试的目的就是希望能以最少的人力和时间发现潜在的各种错误和缺陷。用户应根据开发各阶段的需求、设计等文档或程序的内部结构精心设计测试实例,并利用这些实例来运行程序,以便发现错误的过程。
信息系统测试应包括软件测试、硬件测试和网络测试。硬件测试、网络测试可以根据具体的性能指标进行,此处所说的测试更多的是指软件测试。系统测试是保证系统质量和可靠性的关键步骤,是对系统开发过程中的系统分析、系统设计和实施的最后复查。根据测试的概念和目的,在进行信息系统测试时应遵循以下基本原则。
基本原则(记❤)
- 应尽早并不断地进行测试。测试不是在应用系统开发完之后才进行的。由于原始问题的复杂性、开发各阶段的多样性以及参加人员之间的协调等因素,使得在开发的各个阶段都有可能出现错误。因此,测试应贯穿在开发的各个阶段,应尽早纠正错误,消除隐患。
- 测试工作应该避免由原开发软件的人或小组承担,一方面, 开发人员往往不愿否认自己的工作,总认为自己开发的软件没有错误;另一方面,开发人员的错误很难由本人测试出来,很容易根据自己编程的思路来制定测试思路,具有局限性。测试工作应由专门人员来进行,这样会更客观、更有效。
- 在设计测试方案时,不仅要确定输入数据,而且要根据系统功能确定预期输出结果。将实际输出结果与预期结果相比较就能发现测试对象是否正确。
- 在设计测试用例时,不仅要设计有效、合理的输入条件,也要包含不合理、失效的输入条件。在测试的时候,人们往往习惯按照合理的、正常的情况进行测试,而忽略了对异常、不合理、意想不到的情况进行测试,而这可能就是隐患。
- 在测试程序时,不仅要检验程序是否做了该做的事,还要检验程序是否做了不该做的事。多余的工作会带来副作用,影响程序的效率,有时会带来潜在的危害或错误。
- 严格按照测试计划来进行,避免测试的随意性。测试计划应包括测试内容、进度安排、人员安排、测试环境、测试工具和测试资料等。严格地按照测试计划可以保证进度,使各方面都得以协调进行。
- 妥善保存测试计划、测试用例,作为软件文档的组成部分,为维护提供方便。
- 测试例子都是精心设计出来的,可以为重新测试或追加测试提供方便。当纠正错误、系统功能扩充后,都需要重新开始测试,而这些工作的重复性很高,可以利用以前的测试用例,或在其基础上修改,然后进行测试。
- 系统测试阶段的测试目标来自于需求分析阶段。
测试分类
(1)静态测试
桌前检查、代码走查、代码审查。
(2)动态测试
1、黑盒测试
等价类划分(确定无效与有效等价类,设计用例尽可能多的覆盖有效类,设计用例只覆盖一个无效类)、边界值分析(处理边界情况时最容易出错,选取的测试数据应该恰好等于、稍小于或稍大于边界值)、错误推测、因果图。
2、白盒测试:语句覆盖、判定覆盖、条件覆盖、条件/判定覆盖、路径覆盖。
单元测试
单元测试也称为模块测试,在模块编写完成无编译错误后就可以进行。单元测试侧重于模块中的内部处理逻辑和数据结构。如果选用机器测试,一般用白盒测试法。这类测试可以对多个模块同时进行。
模块接口 | 模块的接口保证了测试模块的数据流可以正确地流入、流出 | |
检 查 要 点 | 测试模块的输入参数和形式参数在个数、属性、单位上是否一致。 | |
调用其他模块时,所给出的实际参数和被调用模块的形式参数在个数、属性、单位上是否一致。 | ||
调用标准函数时,所用的参数在属性、数目和顺序上是否正确。 | ||
全局变量在各模块中的定义和用法是否一致。 | ||
输入是否仅改变了形式参数。 | ||
开/关的语句是否正确。 | ||
规定的I/O格式是否与输入/输出语句一致。 | ||
在使用文件之前是否已经打开文件或使用文件之后是否已经关闭文件。 | ||
局部数据结构 | 在单元测试中,局部数据结构出错是比较常见的错误 | |
重 点 考 虑 因 素 | 变量的说明是否合适 | |
是否使用了尚未赋值或尚未初始化的变量。 | ||
变量的初始值或默认值是否正确。 | ||
变量名是否有错(例如拼写错) | ||
重要的执行路径 | 在单元测试中,对路径的测试是最基本的任务。由于不能进行穷举测试,需要精心设计测试例子来发现是否有计算、比较或控制流等方面的错误。 | |
错 误 | 计算方面的错误。算术运算的优先次序不正确或理解错误;精度不够;运算对象的类型彼此不相容;算法错;表达式的符号表示不正确等。 | |
比较和控制流的错误。本应相等的量由于精度造成不相等;不同类型进行比较;逻辑运算符不正确或优先次序错误;循环终止不正确(如多循环一次或少循环一 次)、 死循环;不恰当地修改循环变量;当遇到分支循环时出口错误等。 | ||
出错处理 | 好的设计应该能预测到出错的条件并且有对出错处理的路径。虽然计算机可以显示出错信息的内容,但仍需要程序员对出错进行处理,保证其逻辑的正确性,以便于用户维护。 | |
边界条件 | 边界条件的测试是单元测试的最后工作,也是非常重要的工作。软件容易在边界出现错误。 |
集成测试
自顶向下:不需要编写驱动模块,需要编写桩模块。
自底向上:不需要编写桩模块,需要编写驱动模块
回归测试
每当加入一个新模块作为集成测试的一部分时,软件发生变更,建立了新的数据流路径,可能出现新的IO,以及调用新的控制逻辑。这些变更可能会使原来可以正常工作的功能产生问题。在集成测试策略的环境下,回归测试是重新执行己测试过的某些子集,以确保变更没有传播不期望的副作用。
回归测试有助于保证变更不引入无意识行为或额外的错误。
黑盒测试
黑盒测试也称为功能测试,在完全不考虑软件的内部结构和特性的情况下,测试软件的外部特性。
常见的黑盒测试技术有:等价类划分、边界值分析、错误推测和因果图。
等价类划分测试方法中,一个测试用例的不合理的输入越多就说明该用例不是一个好的测试用例。
McCabe度量法
白盒测试
白盒测试也称为结构测试,根据程序的内部结构和逻辑来设计测试用例,对程序的路径和过程进行测试,检查是否满足设计的需要。
白盒测试常用的技术是逻辑覆盖、循环覆盖和基本路径测试。
逻辑覆盖。逻辑覆盖考察用测试数据运行被测程序时对程序逻辑的覆盖程度,主要的逻辑覆盖标准有语句覆盖、判定覆盖、条件覆盖、判定/条件覆盖、条件组合覆盖和路径覆盖6种。
- 语句覆盖。语句覆盖是指选择足够的测试数据,使被测试程序中的每条语句至少执行一次。语句覆盖对程序执行逻辑的覆盖很低,因此一般认为它是很弱的逻辑覆盖。
- 判定覆盖。判定覆盖是指设计足够的测试用例,使得被测程序中的每个判定表达式至少获得一次 “真” 值和 “假” 值,或者说是程序中的每一个取“真”分支和取“假”分支至少都通过一次,因此判定覆盖也称为分支覆盖。判定覆盖要比语句覆盖更强一些。
- 条件覆盖。条件覆盖是指构造一组测试用例,使得每一判定 语句中每个逻辑条件的各种可能的值至少满足一次。
- 判定/条件覆盖。判定/条件覆盖是指设计足够的测试用例,使得判定中每个条件的所有可能取值(真/假)至少出现一次,并使每个判定本身的判定结果(真/假)也至少出现一次。
- 条件组合覆盖。条件组合覆盖是指设计足够的测试用例,使得每个判定中条件的各种可能值的组合都至少出现一次。满足条件组合覆盖的测试用例是一定满足判定覆盖、条件覆盖和判定/条件覆盖的。
- 路径覆盖。路径覆盖是指覆盖被测试程序中所有可能的路径。