1、面向对象分析与设计,2,第七章 系统分析,7.1、分析过程概述 在Ripple中,在客户满意之前,分析需要重复经历如下步骤: 1. 使用系统需求模型查找候选的类,以描述与系统相关的对象,并在类图上建立它们 2.确定类之间的关系(关联、聚合、组合、继承) 3.确定类的属性(对象的已指定的简单特性) 4.确定类的操作,检查系统用例,确定已有的对象支持它们,在检查过程中微调类、属性和关系,这个用例的实现过程将生成一些操作。,3,7.2、静态分析,静态建模设计确定系统的逻辑或物理部分,以及如何把它们连接在一起。也就是说,它描述了如何构建和初始化系统。 7.2.1 确定类 以系统用例的形式获得好的候选类
2、,候选类常常在用例中用名词来表示,只要稍微实践一下,就可以快速删除表示下述含义的名词: (1)系统本身 (2)参与者 (3)边界 (4)小类型(字符串或数字),4,7.2.1 确定类,5,7.2.2 正确运用抽象原则,在OOA中正确运用抽象原则 首先要舍弃哪些与系统责任无关的事物,只注意与系统责任有关的事物。 其次,对于与系统责任有关的事物,也不是把它们的任何特征都在相应的对象中表达出来,而要舍弃哪些与系统责任无关的特征。 如何判断事物是否与系统责任有关呢?一是该事物是否为系统提供一些有用的信息,或者它是否需要系统为它保存和管理某些信息。二是它是否向系统提供某些服务,或者,它是否需要系统描述它
3、的某些行为。,6,7.2.3发现类的策略,1、考虑问题域 2、考虑系统边界 3、考虑系统责任,7,7.2.4审查和筛选,找到了候选类后,要对它们逐个进行审查,看看它们是不是OOA模型真正需要的,从而筛选掉一些对象。 1、舍弃无用对象 对于每个候选对象,要判断它在系统中是否真正有用,判断的标准是它们是否提供了有用的属性和服务 A.通过属性判断 B.通过服务判断,8,7.2.4审查和筛选,对象精简 如果系统中的对象的种类及数量过多,则将增加系统的复杂性,应该考虑是否能精简。重点审查 1、只有一个属性的对象 如果对象只有一个属性,应考虑它是被那些对象引用,看看能否合并到这些对象中去。 2、只有一个服
4、务的对象 如果一个对象只有一个服务,没有属性,并且系统中只有一个类的对象请求这个服务,可以考虑将其合并到它的请求者对象中。,9,异常情况的检查和调整,1、类的属性或服务不适合该类的全部对象 2、属性及服务相同的类 3、属性和服务相似的类 4、对同一事物的重复描述,10,7.3标识类的关系,一旦有了候选类列表,就可以绘制出它们之间的关系。有四种类型的关系: 继承:子类继承了超类的所有属性和行为 关联:一种类型的对象与另一种类型的对象关联 聚合:强关联,一个类的实例由另一个类的实例构成。 组合:强聚合,组合的对象不能由其它对象共享,且与构成它的对象一起消亡。,11,7.3标识类的关系,继承与其它三
5、种关系不同:继承描述了类在编译期间的关系,而其它三种关系描述了对象在运行期间的连接关系。根据UML标准,所有运行期间的关系都可以使用同一的术语关联association 但是大多数人把关联看作:既不是聚合也不是复合的关联关系 在关系之间选择时是很困难的,需要使用直觉、经验和推测。在分析过程中这些关系出现的频率。 关联 聚合 继承 组合 就涉及和实现而言,关联、聚合、组合之间的区别很难界定,12,7.4标识类的属性,属性是对象的一个特性,例如对象的大小、位置、名称、价格、颜色等。在UML中每个属性都可以指定一个类型,指定的这个类型可以使类或原型。(在分析阶段也可不指定类型,对提交的、或在设计阶段
6、必须指定一个类型) 属性是描述对象静态特征的一个数据项。 服务是描述对象动态特征的一个操作序列。 属性的命名必须规范。,13,7.4.1发现属性的策略,针对每个对象提出并回答以下问题,从而启发自己从各种角度去发现对象的属性: 1、按一般常识这个对象应该有哪些属性 对象的某些属性,按一般常识就可以知道,例如人的姓名、职业、地址、电话等属性,但要注意,按照一般常识发现的属性未必都有用应该在审查时去掉。 2、在当前的问题域中,这个对象应该有哪些属性 对象的某些属性,只有认真研究问题域才能得到 例如商品的条形码。,14,7.4.1发现属性的策略,3、根据系统责任的要求,这个对象应具有哪些属性 4、建立
7、这个对象是为了保存和管理哪些信息 5、对象为了在服务中实现其功能,需要增设哪些属性 6、对象有哪些需要区别的状态,是否增加一个属性来区别这些状态 7、用什么属性来表示整体-部分结构和实例连接,15,7.4.2审查和筛选,对于初步发现的属性,要进行审查和筛选。为此对每个属性提以下问题: 1、这个属性是否体现了以系统责任 该属性是否提供了系统用的着的信息,OOA应该只注意与系统责任有关的特征 2、这个属性是不是描述这个对象本身的特征 3、该属性是否破坏对象特征的“原子性” 4、这个属性是否可以通过继承得到 5、可以从其他属性直接导出的属性,16,7.4.3属性的命名和定位,属性的命名在词汇使用方面
8、和类的命名基本相同,即: 使用名词或带定语的名词; 使用规范的、问题域通用的词汇; 避免使用无意义的字符和数字; 语言文字的选择与类的命名要一致 总的原则是:一个类的属性必须适合这个类和他全部特殊类的所有对象,并在此前提下充分运用继承。通用的属性放在超类中,专用的属性放在子类中。,17,7.4.3属性详细说明,属性详细说明,主要包括如下信息: 属性的解释 属性的数据类型 属性所体现的关系 用于表示整体-部分关系或实例连接关系的属性,应该特别指出。 实现要求及其他 如:属性的取值范围、精度要求、初始值、度量单位、数据完整性及安全性要求、存取限制条件等。,18,7.5 定义服务,分析员通过分析对象
9、的行为来发现和定义对象的每个服务。但对象的行为往往与对象所处状态相关 状态模型表示方法 状态图 1、什么是对象的状态 有两种理解: 对象或者类的所有属性的当前值 对象或类的整体行为(例如相应消息)的某些规则所能适应的(对象或类的)状况、情况、条件、形式或生成周期阶段。,19,7.5.1行为分类,1、系统行为 2、对象自身的行为 算法简单的服务 算法复杂的服务,20,7.5.2发现服务的策略,1、考虑系统责任 2、考虑问题域 3、分析对象的状态 每一种状态下对象可以发生什么行为 对象从一种状态转换到另一种状态是由什么操作引起的 是否已经设立了相应的服务 4、追踪服务的执行路线 模拟每个服务的执行
10、并追踪器执行路线,可以发现遗漏的服务,又可发现消息连接。,21,7.5.3审查与调整,对每个服务逐个审查,重点审查一下两点。 首先检查每个服务是否真正有用,或者直接提供某种系统责任所要求的功能,或者响应其它对象的请求而间接地完成这种功能的某些局部操作。 其次是检查每个服务是不是高内聚。所谓高内聚是指一个服务只完成一项明确定义的、完整而单一的功能。如果一个服务中包括多项可独立定义的功能,则它是低内聚的。,22,7.5.4服务的命名和定位,服务的命名应采用动词或动词加名词所组成的动宾结构,服务名应尽可能准确地反映该服务的功能。 服务放置在哪个对象,应和问题域中拥有这种行为和责任的实际事物相一致。例
11、如商场管理系统中,“售货”服务应放在“售货员”对象中而不应放在货物中。 在一般-特殊结构中和属性的定位原则一样,通用的服务放在超类中,专用服务放在子类中。,23,7.5.5服务的详细说明,服务解释:解释该服务的 消息协议:给出服务的入口的消息格式,即请求该服务的消息格式,内容包括:服务名,输入输出参数,参数类型。 消息发送:指出在这个服务执行时,需要请求那些别的服务,内容包括接受消息的对象类名以及执行这个消息的服务名。 约束条件:该服务执行有前置条件,后置条件以及执行时间要求等其它说明事项。,24,7.6 选择属性还是关系,25,7.6 选择属性还是关系,上述设计都可行,只是其中一些显得有点违
12、背常理。该选择哪个选项呢? 中心议题是:那个建模选项最适合当前的情况?换言之,那个选项最自然,就选项1而言,说color是Car的一部分显得有点笨拙。选项2似乎有点好,就汽车买主而言,颜色只是汽车的一个属性。4可能比1好些:汽车出厂都会喷一种颜色。 总之,2在购买汽车时是最合适的,26,7.6 选择属性还是关系,如果从汽车厂家的角度给汽车建模,会不同吗? 在这种情况下颜料厂家可能比较重要, 如果颜料用光了,我们需要知道到哪里可购买颜料。所以需要把Color建立一个单独的类,且有自己的关系和属性,因此4是最好的选择 如果心理学家要了解汽车的颜色对司机行为的影响,也许红色的汽车会激发危险的驾驶行为,而绿色的汽车可使司机谨慎驾驶。在这种情况下,红色和绿色的汽车完全不同,应给他们单独建模,3就是最好的,27,7.6 选择属性还是关系,如果在汽车修配厂,需要给汽车喷不同颜色漆,这时候可能1是最好的选择。 这个例子说明,分析员必须选择最合适当前情况的表达方式,这是没有固定答案的,要利用常识、经验、直觉、反复斟酌,找出最合适的实现方式。,28,7.7关联类,关联偶尔也有与他相关的信息和行为。关联类可以和关联类一起引入,