Software design is a creative process.It requires a certain amount of flair on the part of the designer and the final design is normally an iteration from a number of preliminary designs.Design cannot be learned from a book—it must be practiced and learnt by experience and study of existing systems.Good design is the key to effective software engineering.A well-designed software system is straightforward [1] to implement and maintain,easily understood and reliable.Badly designed systems,although they may work,are likely to be expensive to maintain,difficult to test and unreliable.The design stage is therefore the most critical part of the software development process.
Until fairly recently,software design was largely an ad hoc[2] process.Given a set of requirements,usually in natural language,an informal design was prepared,often in the form of a flowchart[3].Coding then commenced and the design was modified as the system was implemented.When the implementation stage was complete,the design had usually changed so much from its initial specification that the original design document was a totally inadequate description of the system.
This approach to software design was responsible for many dramatic and very expensive project failures.Now it is realized that completely informal notations such as flowcharts,which are close to the programming language,are inadequate vehicles for formulating and expressing system design.It is recognized that precise(although not necessarily formal)specification is an essential part of the design process and that software design is an iterative,multi-stage activity which cannot be represented in any single notation.Accordingly,a number of design notations such as data flow diagrams.HIPO charts[4],structure diagrams and design description languages have been developed which are superior to flowcharts for expressing software designs.
Given a requirements definition,the software engineer must use this to derive the design of a programming system which satisfies these requirements.This derivation is accomplished in a number of stages:
(1)The subsystems making up the programming system must be established.
(2)Each subsystem must be decomposed into separate components and the subsystem specification established by defining the operation of these components.
(3)Each program may then be designed in terms of interacting subcomponents.
(4)Each component must then be refined.This normally entails specifying each component as hierarchy of subcomponents.
(5)At some stage of this refinement process,the algorithms used in each component must be specified in detail.
As well as these various stages of programming system design,the software engineer may also be required to design communication mechanisms allowing processes in the system to communicate[5].He or she may have to design file structures,and will almost certainly have to design the data structures used in his programs.He or she will have to design test cases to validate his programs.
There is no definitive way of establishing what is meant by a“good”design.Depending on the application and the particular project requirements,a good design might be a design which allows very efficient code to be produced,it might be a minimal design where the implementation is as compact as possible,or it might be the most maintainable design.This latter criterion is the criterion of“goodness”adopted here.A maintainable design implies that the cost of system changes is minimized and this means that the design should be understandable and that changes should be local in effect.Both of these are achieved if the software design is highly cohesive and loosely coupled[6].
Effective software design is best accomplished by using a consistent design methodology.There have been a vast number of design methodologies developed and used in different applications.Some of these are described by Peters(1980)and by Blank and Krijger(1983).In essence,most of these methodologies can be classified into one of three areas:
(1)Top-down functional design.The system is designed from a functional viewpoint,starting with a high-level view and progressively refining this into a more detailed design.This methodology is exemplified by Structured Design and stepwise refinement.
(2)Object-oriented design.The system is viewed as a collection of objects rather than as functions with messages passed from object to object.Each object has its own set of associated operations.Object-oriented design is based on the idea of information hiding which was first put forward by Parnas(1972)and which has been described more recently by Robson(1981)and Booch(1983).
(3)Data-driven design.This methodology,suggested by Jackson(1975)and Warnier(1977)suggests that the structure of a software system should reflect the structure of the data processed by that system.Therefore,the software design is derived from an analysis of the input and output system data.
NOTES
[1] straightforward:直接了当的,简单明了的。
[2] ad hoc:特别的(地)。
[3] flowchart:流程图。
[4] HIPO charts:层次输入一处理一输出图。
[5] allowing... :修饰communication mechanisms。
[6] loosely coupled:松散地耦合。
KEYWORDS
software design 软件设计
object-oriented design 面向目标的设计
maintainable design 可维护性设计
data-driven design 数据驱动的设计
top-down functional design 自顶向下的功能设计
翻译:
软件设计是一个创造性的过程,对一些设计者来说需要一定的资质,而最后设计通常都是由若于初步设计反复比较而来。从书本上学不会设计,只能经过实践.通过对一现有系统的研究和实际演练才能做到。对于能产生预期结果的软件工程,良好的设计是关键。设计得好的软件系统实现和维护方式简单明了、易懂可靠。设计得不好的系统,尽管可以工作,但很可能维护费高、测试困难且不可靠。因此,设计阶段是软件开发过程中最重要的阶段。
直到最近,软件设计在很大程度上仍是一个特定过程。一般用自然语言,给定一系列需求,准备好非正式设计,并常常用流程图的形式说明;接着开始编码;当系统实现时设计还会修改。当实现阶段完成后,设计往往与当初的规格说明相去甚远,以至于原始文档完全不适合对系统的描述。
软件设计的这种方法导致了许多惊人的而且是代价很大的工程失败。现在已经认识到一些完全非正式的表示法,诸如接近于编程语言的流程图,不适用于系统设计的公式化和表达。大家认识到,精确(尽管并不一定是正式)的规格说明是设计过程的必要部分。软件设计是一个反复的、不能用任何单一表示法来表示的多阶段活动。相应地,大量的设计表示法,如数据流图、层次化输入一处理一输出结构图和设计描述语言已经开发出来,比流程图能更好地表达软件设计。
对于给定的需求定义,软件工程师必须据此导出满足这些需求的程序系统的设计。此导出过程是通过下述步骤来完成的:
(1)必须建立组成程序系统的子系统;
(2)必须把每个子系统分解成独立的成分,并且通过定义这些成分的操作来建立子系统规格说明;
(3)每个程序可以用相互作用的子成分设计;
(4)每个成分还须进行优化,这通常需要将每个成分规定为层次式的子成分;
(5)在精化过程中的某个阶段,各成分中的算法必须详细规定。
除了程序系统设计中的这些阶段之外,软件工程师也可能需要设计允许系统中各进程之间进行通信的通信机制。他们或许要设计文件结构,并且几乎必然要设计用于程序的数据结构,他们还需要设计确认程序的测试用例。
确定何为“成功”的设计无一定之规。依据应用和特定的工程要求。一个成功的设计应该是:能生成高效的代码,实现尽量紧凑的最小设计或最易维护的设计。最后一个准则是本文采用的优良度准则。可维护性设计意指系统修改费用最低,设计易于理解和修改是局部性的。只有高度内聚而又松散藕合的软件设计才能实现以上两个目标。
有效的软件设计最好利用一致性设计方法学。有大量的在不同应用环境中开发并使用的设计方法学。其中有些是由Yeters(1980),Blank 和 Krijger(1983)阐述的。实质上,这些方法学大多数和划分为3类。
(1)自顶向下的功能设计:从功能的观点设计系统,从高层的观点着手逐步提炼成更具体的设计。结构化设计和逐步求精就是使用此方法的例子。
(2)面向对象的设计:把系统作为对象集合而不是功能的集合,消息在对象与对象之间传送,每个对象都有自己的关联操作集。面向对象的设计方法是基于信息隐藏的思想,该思想由Parnas(1972)最先提出,最近又由Robson(1981)和Booch(1983)加以描述。
(3)数据驱动的设计:此方法由Jackson(1975)和Warnier(1977)提出,认为软件系统的结构应该反映该系统所处理的数据的结构。因此,软件设计应从对系统输入、输出数据进行分析中导出。