7 The static structure:classes minng the software background ofiscussyou have reasons for demanding a better approach to modular design:reusability and extendibility You have realized the limitations of traditional approaches:centralized architectures limiting flexibility.You have discovered the theory behind the object-oriented approach: abstract data types.You have heard enough about the problems.On to the solution! This chapter and the others in part C introduce the fundamental techniques of object- oriented analysis,design and programming.As we go along,we will develop the necessary notation. Our first task is to examine the basic building blocks:classes. 7.1 OBJECTS ARE NOT THE SUBJECT What is the central concept of object technology? Think twice before you answer "object".Objects are useful,but they are not new. Ever since Cobol has had structures;ever since Pascal has had records;ever since the first C programmer wrote the first C structure definition,humanity has had objects. Objects are stud- Objects remain important to describe the execution of an O-O system.But the basic iedinderailin the notion,from which everything in object technology derives,is class,previewed in the next chapter. preceding chapter.Here again is the definition: Definition:class A class is an abstract data type equipped with a possibly partial implementation. Abstract data types are a mathematical notion,suitable for the specification stage (also called analysis).Because it introduces implementations,partial or total,the notion of class establishes the necessary link with software construction -design and implementation.Remember that a class is said to be effective if the implementation is total,deferred otherwise
7 The static structure: classes Examining the software engineering background of our discussion, you have seen the reasons for demanding a better approach to modular design: reusability and extendibility. You have realized the limitations of traditional approaches: centralized architectures limiting flexibility. You have discovered the theory behind the object-oriented approach: abstract data types. You have heard enough about the problems. On to the solution! This chapter and the others in part C introduce the fundamental techniques of objectoriented analysis, design and programming. As we go along, we will develop the necessary notation. Our first task is to examine the basic building blocks: classes. 7.1 OBJECTS ARE NOT THE SUBJECT What is the central concept of object technology? Think twice before you answer “object”. Objects are useful, but they are not new. Ever since Cobol has had structures; ever since Pascal has had records; ever since the first C programmer wrote the first C structure definition, humanity has had objects. Objects remain important to describe the execution of an O-O system. But the basic notion, from which everything in object technology derives, is class, previewed in the preceding chapter. Here again is the definition: Abstract data types are a mathematical notion, suitable for the specification stage (also called analysis). Because it introduces implementations, partial or total, the notion of class establishes the necessary link with software construction — design and implementation. Remember that a class is said to be effective if the implementation is total, deferred otherwise. Definition: class A class is an abstract data type equipped with a possibly partial implementation. Objects are studied in detail in the next chapter
166 THE STATIC STRUCTURE:CLASSES $7.2 Like an ADT,a class is a type:it describes a set of possible data structures,called the instances of the class.Abstract data types too have instances;the difference is that an instance of an ADT is a purely mathematical element(a member of some mathematical set),whereas an instance of a class is a data structure that may be represented in the memory of a computer and manipulated by a software system. For example if we have defined a class STACK by taking the ADT specification of the previous chapter and adding adequate representation information,the instances of that class will be data structures representing individual stacks.Another example,developed in the rest of this chapter,is a class PO/N7 modeling the notion of point in a two- dimensional space,under some appropriate representation;an instance of that class is a data structure representing a point.Under one of the representations studied below,the cartesian representation,each instance of POINT is a record with two fields representing the horizontal and vertical coordinates,x and y,of a point. The definition of"class"yields as a byproduct a definition of"object".An object is simply an instance of some class.For example an instance of class STACK-a data structure representing a particular stack-is an object;so is an instance of class PO/N7, representing a particular point in two-dimensional space. The software texts that serve to produce systems are classes.Objects are a run-time notion only:they are created and manipulated by the software during its execution. The present chapter is devoted to the basic mechanisms for writing software elements and combining them into systems;as a consequence,its focus is on classes.In the next chapter,we will explore the run-time structures generated by an object-oriented system;this will require us to study some implementation issues and to take a closer look at the nature of objects. 7.2 AVOIDING THE STANDARD CONFUSION A class is a model,and an object is an instance of such a model.This property is so obvious The next section,for that it would normally deserve no comments beyond the preceding definitions;but is has readers who do not been the victim of so much confusion in the more careless segment of the literature that like the belaboring of the obvious,is we must take some time to clarify the obvious.(If you feel that you are immune to such a “THE ROLE OF danger,and have avoided exposure to sloppy object-oriented teaching,you may wish to CLASSES”,7.3, skip this section altogether as it essentially belabors the obvious. page 169. What would you think of this? Among the countries in Europe we may identify the Italian.The Italian has a mountain chain running through him North-South and he likes good cooking,often using olive oil.His climate is of the Mediterranean type,and he speaks a beautifully musical language
166 THE STATIC STRUCTURE: CLASSES §7.2 Like an ADT, a class is a type: it describes a set of possible data structures, called the instances of the class. Abstract data types too have instances; the difference is that an instance of an ADT is a purely mathematical element (a member of some mathematical set), whereas an instance of a class is a data structure that may be represented in the memory of a computer and manipulated by a software system. For example if we have defined a class STACK by taking the ADT specification of the previous chapter and adding adequate representation information, the instances of that class will be data structures representing individual stacks. Another example, developed in the rest of this chapter, is a class POINT modeling the notion of point in a twodimensional space, under some appropriate representation; an instance of that class is a data structure representing a point. Under one of the representations studied below, the cartesian representation, each instance of POINT is a record with two fields representing the horizontal and vertical coordinates, x and y, of a point. The definition of “class” yields as a byproduct a definition of “object”. An object is simply an instance of some class. For example an instance of class STACK — a data structure representing a particular stack — is an object; so is an instance of class POINT, representing a particular point in two-dimensional space. The software texts that serve to produce systems are classes. Objects are a run-time notion only: they are created and manipulated by the software during its execution. The present chapter is devoted to the basic mechanisms for writing software elements and combining them into systems; as a consequence, its focus is on classes. In the next chapter, we will explore the run-time structures generated by an object-oriented system; this will require us to study some implementation issues and to take a closer look at the nature of objects. 7.2 AVOIDING THE STANDARD CONFUSION A class is a model, and an object is an instance of such a model. This property is so obvious that it would normally deserve no comments beyond the preceding definitions; but is has been the victim of so much confusion in the more careless segment of the literature that we must take some time to clarify the obvious. (If you feel that you are immune to such a danger, and have avoided exposure to sloppy object-oriented teaching, you may wish to skip this section altogether as it essentially belabors the obvious.) What would you think of this? Among the countries in Europe we may identify the Italian. The Italian has a mountain chain running through him North-South and he likes good cooking, often using olive oil. His climate is of the Mediterranean type, and he speaks a beautifully musical language. The next section, for readers who do not like the belaboring of the obvious, is “THE ROLE OF CLASSES”, 7.3, page 169
$7.2 AVOIDING THE STANDARD CONFUSION 167 See e.g.Oliver If someone in a sober state talked or wrote to you in this fashion,you might suspect a new Sacks,The Man neurological disease,the inability to distinguish between categories(such as the Italian Who Mistook His Wife for a Hat and nation)and individuals members of these categories (such as individual Italians),reason Other Clinical enough to give to the ambulance driver the address of Dr.Sacks's New York clinic Tales",Harper Perennials,1991. Yet in the object-oriented software literature similar confusions are common. Consider the following extract from a popular book on O-O analysis,which uses the example of an interactive system to discuss how to identify abstractions: [Coad1990]3.3.3, [Wle might identify a "User"Object in a problem space where the system page 67. does not need to keep any information about the user.In this case,the system does not need the usual identification number,name,access privilege,and the like.However,the system does need to monitor the user,responding to requests and providing timely information.And so,because of required Services on behalfof the real world thing (in this case,User),we need to add a corresponding Object to the model of the problem space. In the same breath this text uses the word objects,user and thing in two meanings belonging to entirely different levels of abstraction: Exercise E7.1,page A typical user of the interactive system under discussion. 216,asks you to clarify each use of The concept of user in general. “Object”in this tex.. Although this is probably a slip of terminology(a peccadillo which few people can claim never to have committed)rather than a true confusion on the authors'part,it is unfortunately representative of how some of the literature deals with the model-instance distinction.If you start the study of a new method with this kind of elementary mix-up, real or apparent,you are not likely to obtain a rational approach to software construction. The mold and the instance Take this book-the copy which you are currently reading.Consider it as an object in the common sense of the term.It has its own individual features:the copy may be brand new, or already thumbed by previous readers;perhaps you wrote your name on the first page; or it belongs to a library and has a local identification code impressed on its spine. The basic properties of the book,however,such as its title,publisher,author and contents,are determined by a general description which applies to every individual copy: the book is entitled Object-Oriented Software Construction,it is published by Prentice Hall,it talks about the object-oriented method,and so on.This set of properties defines not an object but a class of objects(also called,in this case,the type of these objects;for the time being the notions of type and class may be considered synonymous). Call the class OOSC.It defines a certain mold.Objects built from this mold,such as your copy of the book,are called instances of the class.Another example of mold would be the plaster cast that a sculptor makes to obtain an inverted version of the design for a set of identical statues;any statue derived from the cast is an instance of the mold
§7.2 AVOIDING THE STANDARD CONFUSION 167 If someone in a sober state talked or wrote to you in this fashion, you might suspect a new neurological disease, the inability to distinguish between categories (such as the Italian nation) and individuals members of these categories (such as individual Italians), reason enough to give to the ambulance driver the address of Dr. Sacks’s New York clinic. Yet in the object-oriented software literature similar confusions are common. Consider the following extract from a popular book on O-O analysis, which uses the example of an interactive system to discuss how to identify abstractions: In the same breath this text uses the word objects, user and thing in two meanings belonging to entirely different levels of abstraction: • A typical user of the interactive system under discussion. • The concept of user in general. Although this is probably a slip of terminology (a peccadillo which few people can claim never to have committed) rather than a true confusion on the authors’ part, it is unfortunately representative of how some of the literature deals with the model-instance distinction. If you start the study of a new method with this kind of elementary mix-up, real or apparent, you are not likely to obtain a rational approach to software construction. The mold and the instance Take this book — the copy which you are currently reading. Consider it as an object in the common sense of the term. It has its own individual features: the copy may be brand new, or already thumbed by previous readers; perhaps you wrote your name on the first page; or it belongs to a library and has a local identification code impressed on its spine. The basic properties of the book, however, such as its title, publisher, author and contents, are determined by a general description which applies to every individual copy: the book is entitled Object-Oriented Software Construction, it is published by Prentice Hall, it talks about the object-oriented method, and so on. This set of properties defines not an object but a class of objects (also called, in this case, the type of these objects; for the time being the notions of type and class may be considered synonymous). Call the class OOSC. It defines a certain mold. Objects built from this mold, such as your copy of the book, are called instances of the class. Another example of mold would be the plaster cast that a sculptor makes to obtain an inverted version of the design for a set of identical statues; any statue derived from the cast is an instance of the mold. [W]e might identify a “User” Object in a problem space where the system does not need to keep any information about the user. In this case, the system does not need the usual identification number, name, access privilege, and the like. However, the system does need to monitor the user, responding to requests and providing timely information. And so, because of required Services on behalf of the real world thing (in this case, User), we need to add a corresponding Object to the model of the problem space. See e.g. Oliver Sacks, ``The Man Who Mistook His Wife for a Hat and Other Clinical Tales'', Harper Perennials, 1991. [Coad 1990], 3.3.3, page 67. Exercise E7.1, page 216, asks you to clarify each use of “Object” in this text
168 THE STATIC STRUCTURE:CLASSES $7.2 In the quotation from The Name ofthe Rose which opens part C,the Master is explaining Page 163. how he was able to determine,from traces of the snow,that Brownie,the Abbot's horse, earlier walked here.Brownie is an instance of the class of all horses.The sign on the snow,although imprinted by one particular instance,includes only enough information to determine the class (horse),not its identity (Brownie).Since the class,like the sign, identifies all horses rather than a particular horse,the extract calls it a sign too. Exactly the same concepts apply to software objects.What you will write in your software systems is the description of classes,such as a class LINKED STACK describing properties of stacks in a certain representation.Any particular execution of your system may use the classes to create objects(data structures);each such object is derived from a class,and is called an instance of that class.For example the execution may create a linked stack object,derived from the description given in class LINKED STACK;such an object is an instance of class LINKED STACK. The class is a software text.It is static;in other words,it exists independently ofany execution.In contrast,an object derived from that class is a dynamically created data structure,existing only in the memory of a computer during the execution of a system. This,of course,is in line with the earlier discussion of abstract data types:when specifying STACK as an ADT,we did not describe any particular stack,but the general notion of stack,a mold from which one can derive individual instances ad libitum. The statements "x is an instance of T"and"x is an object of type T"will be considered synonymous for this discussion. With the introduction of inheritance we will need to distinguish between the direct See“Instances” instances of a class(built from the exact pattern defined by the class)and its instances in page 475. the more general sense (direct instances of the class or any of its specializations). Metaclasses Why would so many books and articles confuse two so clearly different notions as class and object?One reason一although not an excuse一is the appeal of the word“object”,a simple term from everyday language.But it is misleading.As we already saw in the discussion of seamlessness,although some of the objects (class instances)which O-O systems manipulate are the computer representations of objects in the usual sense of the term,such as documents,bank accounts or airplanes,many others have no existence outside of the software;they include in particular the objects introduced for design and implementation purposes-instances of classes such as STATE or LINKED L/ST Another possible source of confusion between objects and classes is that in some cases we may need to treat classes themselves as objects.This need arises only in special contexts,and is mainly relevant to developers of object-oriented development environments.For example a compiler or interpreter for an O-O language will manipulate data structures representing classes written in that language.The same would hold of other tools such as a browser (a tool used to locate classes and find out about their properties) or a configuration management system.If you produce such tools,you will create objects that represent classes
168 THE STATIC STRUCTURE: CLASSES §7.2 In the quotation from The Name of the Rose which opens part C, the Master is explaining how he was able to determine, from traces of the snow, that Brownie, the Abbot’s horse, earlier walked here. Brownie is an instance of the class of all horses. The sign on the snow, although imprinted by one particular instance, includes only enough information to determine the class (horse), not its identity (Brownie). Since the class, like the sign, identifies all horses rather than a particular horse, the extract calls it a sign too. Exactly the same concepts apply to software objects. What you will write in your software systems is the description of classes, such as a class LINKED_STACK describing properties of stacks in a certain representation. Any particular execution of your system may use the classes to create objects (data structures); each such object is derived from a class, and is called an instance of that class. For example the execution may create a linked stack object, derived from the description given in class LINKED_STACK; such an object is an instance of class LINKED_STACK. The class is a software text. It is static; in other words, it exists independently of any execution. In contrast, an object derived from that class is a dynamically created data structure, existing only in the memory of a computer during the execution of a system. This, of course, is in line with the earlier discussion of abstract data types: when specifying STACK as an ADT, we did not describe any particular stack, but the general notion of stack, a mold from which one can derive individual instances ad libitum. The statements “x is an instance of T” and “x is an object of type T” will be considered synonymous for this discussion. With the introduction of inheritance we will need to distinguish between the direct instances of a class (built from the exact pattern defined by the class) and its instances in the more general sense (direct instances of the class or any of its specializations). Metaclasses Why would so many books and articles confuse two so clearly different notions as class and object? One reason — although not an excuse — is the appeal of the word “object”, a simple term from everyday language. But it is misleading. As we already saw in the discussion of seamlessness, although some of the objects (class instances) which O-O systems manipulate are the computer representations of objects in the usual sense of the term, such as documents, bank accounts or airplanes, many others have no existence outside of the software; they include in particular the objects introduced for design and implementation purposes — instances of classes such as STATE or LINKED_LIST. Another possible source of confusion between objects and classes is that in some cases we may need to treat classes themselves as objects. This need arises only in special contexts, and is mainly relevant to developers of object-oriented development environments. For example a compiler or interpreter for an O-O language will manipulate data structures representing classes written in that language. The same would hold of other tools such as a browser (a tool used to locate classes and find out about their properties) or a configuration management system. If you produce such tools, you will create objects that represent classes. Page 163. See “Instances”, page 475
$7.3 THE ROLE OF CLASSES 169 Pursuing an analogy used earlier,we may compare this situation to that of a Prentice Hall employee who is in charge of preparing the catalog of software engineering titles.For the catalog writer,OOSC,the concept behind this book,is an object-an instance of a class "catalog entry".In contrast,for the reader of the book,that concept is a class,of which the reader's particular copy is an instance. Some object-oriented languages,notably Smalltalk,have introduced a notion of metaclass to handle this kind of situation.A metaclass is a class whose instances are themselves classes-what the Name of the Rose extract called"signs of signs". We will avoid metaclasses in this presentation,however,since they bring more problems than benefits.In particular,the addition of metaclasses makes it difficult to have static type checking,a required condition of the production of reliable software.The main applications of metaclasses are better obtained through other mechanisms anyway: “Universal c☑lasses” You can use metaclasses to make a set of features available to many or all classes page 580. We will achieve the same result by arranging the inheritance structure so that all classes are descendants of a general-purpose,customizable class ANY,containing the declarations of universal features. See“The creation A few operations may be viewed as characterizing a class rather than its instances, instruction",page justifying their inclusion as features of a metaclass.But these operations are few and 232. known;the most obvious one is object creation-sufficiently important to deserve a special language construct,the creation instruction.(Other such operations,such as object duplication,will be covered by features of class ANY.) There remains the use of metaclasses to obtain information about a class,such as a browser may need:name of the class,list of features,list of parents,list of suppliers etc.But we do not need metaclasses for that.It will suffice to devise a library class, E CLASS,so that each instance of E CLASS represents a class and its properties. When we create such an instance,we pass to the creation instruction an argument representing a certain class C;then by applying the various features of E CLASS to that instance,we can learn all about C. In practice,then,we can do without a separate concept of metaclass.But even in a method,language or environment that would support this notion,the presence of metaclasses is no excuse for confusing molds and their instances-classes and objects. 7.3 THE ROLE OF CLASSES Having taken the time to remove an absurd but common and damaging confusion,we may now come back to the central properties ofclasses,and in particular study why they are so important to object technology. To understand the object-oriented approach,it is essential to realize that classes play two roles which pre-O-O approaches had always treated as separate:module and type
§7.3 THE ROLE OF CLASSES 169 Pursuing an analogy used earlier, we may compare this situation to that of a Prentice Hall employee who is in charge of preparing the catalog of software engineering titles. For the catalog writer, OOSC, the concept behind this book, is an object — an instance of a class “catalog entry”. In contrast, for the reader of the book, that concept is a class, of which the reader’s particular copy is an instance. Some object-oriented languages, notably Smalltalk, have introduced a notion of metaclass to handle this kind of situation. A metaclass is a class whose instances are themselves classes — what the Name of the Rose extract called “signs of signs”. We will avoid metaclasses in this presentation, however, since they bring more problems than benefits. In particular, the addition of metaclasses makes it difficult to have static type checking, a required condition of the production of reliable software. The main applications of metaclasses are better obtained through other mechanisms anyway: • You can use metaclasses to make a set of features available to many or all classes. We will achieve the same result by arranging the inheritance structure so that all classes are descendants of a general-purpose, customizable class ANY, containing the declarations of universal features. • A few operations may be viewed as characterizing a class rather than its instances, justifying their inclusion as features of a metaclass. But these operations are few and known; the most obvious one is object creation — sufficiently important to deserve a special language construct, the creation instruction. (Other such operations, such as object duplication, will be covered by features of class ANY.) • There remains the use of metaclasses to obtain information about a class, such as a browser may need: name of the class, list of features, list of parents, list of suppliers etc. But we do not need metaclasses for that. It will suffice to devise a library class, E_CLASS, so that each instance of E_CLASS represents a class and its properties. When we create such an instance, we pass to the creation instruction an argument representing a certain class C; then by applying the various features of E_CLASS to that instance, we can learn all about C. In practice, then, we can do without a separate concept of metaclass. But even in a method, language or environment that would support this notion, the presence of metaclasses is no excuse for confusing molds and their instances — classes and objects. 7.3 THE ROLE OF CLASSES Having taken the time to remove an absurd but common and damaging confusion, we may now come back to the central properties of classes, and in particular study why they are so important to object technology. To understand the object-oriented approach, it is essential to realize that classes play two roles which pre-O-O approaches had always treated as separate: module and type. “Universal classes”, page 580. See “The creation instruction”, page 232
170 THE STATIC STRUCTURE:CLASSES $7.3 Modules and types Programming languages and other notations used in software development (design languages,specification languages,graphical notations for analysis)always include both some module facility and some type system. A module is a unit of software decomposition.Various forms of module,such as See chapter 3. routines and packages,were studied in an earlier chapter.Regardless of the exact choice of module structure,we may call the notion of module a syntactic concept,since the decomposition into modules only affects the form of software texts,not what the software can do;it is indeed possible in principle to write any Ada program as a single package,or any Pascal program as a single main program.Such an approach is not recommended,of course,and any competent software developer will use the module facilities of the language at hand to decompose his software into manageable pieces.But if we take an existing program,for example in Pascal,we can always merge all the modules into a single one,and still get a working system with equivalent semantics.(The presence of recursive routines makes the conversion process less trivial,but does not fundamentally affect this discussion.)So the practice of decomposing into modules is dictated by sound engineering and project management principles rather than intrinsic necessity. Types,at first sight,are a quite different concept.A type is the static description of certain dynamic objects:the various data elements that will be processed during the execution ofa software system.The set of types usually includes predefined types such as INTEGER and CHARACTER as well as developer-defined types:record types (also known as structure types),pointer types,set types(as in Pascal),array types and others. The notion of type is a semantic concept,since every type directly influences the execution of a software system by defining the form of the objects that the system will create and manipulate at run time. The class as module and type In non-O-0 approaches,the module and type concepts remain distinct.The most remarkable property of the notion of class is that it subsumes these two concepts,merging them into a single linguistic construct.A class is a module,or unit of software decomposition;but it is also a type (or,in cases involving genericity,a type pattern) Much of the power of the object-oriented method derives from this identification. Inheritance,in particular,can only be understood fully if we look at it as providing both module extension and type specialization. What is not clear yet is how it is possible in practice to unify two concepts which appear at first so distant.The discussion and examples in the rest of this chapter will answer this question
170 THE STATIC STRUCTURE: CLASSES §7.3 Modules and types Programming languages and other notations used in software development (design languages, specification languages, graphical notations for analysis) always include both some module facility and some type system. A module is a unit of software decomposition. Various forms of module, such as routines and packages, were studied in an earlier chapter. Regardless of the exact choice of module structure, we may call the notion of module a syntactic concept, since the decomposition into modules only affects the form of software texts, not what the software can do; it is indeed possible in principle to write any Ada program as a single package, or any Pascal program as a single main program. Such an approach is not recommended, of course, and any competent software developer will use the module facilities of the language at hand to decompose his software into manageable pieces. But if we take an existing program, for example in Pascal, we can always merge all the modules into a single one, and still get a working system with equivalent semantics. (The presence of recursive routines makes the conversion process less trivial, but does not fundamentally affect this discussion.) So the practice of decomposing into modules is dictated by sound engineering and project management principles rather than intrinsic necessity. Types, at first sight, are a quite different concept. A type is the static description of certain dynamic objects: the various data elements that will be processed during the execution of a software system. The set of types usually includes predefined types such as INTEGER and CHARACTER as well as developer-defined types: record types (also known as structure types), pointer types, set types (as in Pascal), array types and others. The notion of type is a semantic concept, since every type directly influences the execution of a software system by defining the form of the objects that the system will create and manipulate at run time. The class as module and type In non-O-O approaches, the module and type concepts remain distinct. The most remarkable property of the notion of class is that it subsumes these two concepts, merging them into a single linguistic construct. A class is a module, or unit of software decomposition; but it is also a type (or, in cases involving genericity, a type pattern). Much of the power of the object-oriented method derives from this identification. Inheritance, in particular, can only be understood fully if we look at it as providing both module extension and type specialization. What is not clear yet is how it is possible in practice to unify two concepts which appear at first so distant. The discussion and examples in the rest of this chapter will answer this question. See chapter 3
$7.4 A UNIFORM TYPE SYSTEM 171 7.4 A UNIFORM TYPE SYSTEM An important aspect of the O-O approach as we will develop it is the simplicity and uniformity of the type system,deriving from a fundamental property: Object rule Every object is an instance of some class. The Object rule will apply not just to composite,developer-defined objects(such as data structures with several fields)but also to basic objects such as integers,real numbers boolean values and characters,which will all be considered to be instances of predefined library classes (INTEGER,REAL,DOUBLE,BOOLEAN,CHARACTER). This zeal to make every possible value,however simple,an instance of some class may at first appear exaggerated or even extravagant.After all,mathematicians and engineers have used integers and reals successfully for a long time,without knowing they were manipulating class instances.But insisting on uniformity pays off for several reasons: It is always desirable to have a simple and uniform framework rather than many special cases.Here the type system will be entirely based on the notion of class. The mathematical Describing basic types as ADTs and hence as classes is simple and natural.It is not axioms defining hard,for example,to see how to define the class INTEGER with features covering integers are known as Peano's axioms. arithmetic operations such as "+"comparison operations such as"<=",and the associated properties,derived from the corresponding mathematical axioms. By defining the basic types as classes,we allow them to take part in all the O-O games,especially inheritance and genericity.If we did not treat the basic types as classes,we would have to introduce severe limitations and many special cases. As an example of inheritance,classes /NTEGER,REAL and DOUBLE will be heirs to more general classes:NUMER/C,introducing the basic arithmetic operations such as "+"," and ""and COMPARABLE,introducing comparison operations such as "<"As an example of genericity,we can define a generic class MATRIY whose generic parameter represents the type of matrix elements,so that instances of MATRIY [INTEGER]represent matrices of integers,instances of MATR/Y [REAL]represent matrices of reals and so on.As an example of combining genericity with inheritance,the preceding definitions also allow us to use the type MATRIY [NUMER/C],whose instances represent matrices containing objects of type INTEGER as well as objects of type REAL and objects of any new type T defined by a software developer so as to inherit from NUMER/C. With a good implementation,we do not need to fear any negative consequence from the decision to define all types from classes.Nothing prevents a compiler from having special knowledge about the basic classes;the code it generates for operations on values of types such as INTEGER and BOOLEAN can then be just as efficient as if these were built-in types in the language
§7.4 A UNIFORM TYPE SYSTEM 171 7.4 A UNIFORM TYPE SYSTEM An important aspect of the O-O approach as we will develop it is the simplicity and uniformity of the type system, deriving from a fundamental property: The Object rule will apply not just to composite, developer-defined objects (such as data structures with several fields) but also to basic objects such as integers, real numbers, boolean values and characters, which will all be considered to be instances of predefined library classes (INTEGER, REAL, DOUBLE, BOOLEAN, CHARACTER). This zeal to make every possible value, however simple, an instance of some class may at first appear exaggerated or even extravagant. After all, mathematicians and engineers have used integers and reals successfully for a long time, without knowing they were manipulating class instances. But insisting on uniformity pays off for several reasons: • It is always desirable to have a simple and uniform framework rather than many special cases. Here the type system will be entirely based on the notion of class. • Describing basic types as ADTs and hence as classes is simple and natural. It is not hard, for example, to see how to define the class INTEGER with features covering arithmetic operations such as "+", comparison operations such as "<=", and the associated properties, derived from the corresponding mathematical axioms. • By defining the basic types as classes, we allow them to take part in all the O-O games, especially inheritance and genericity. If we did not treat the basic types as classes, we would have to introduce severe limitations and many special cases. As an example of inheritance, classes INTEGER, REAL and DOUBLE will be heirs to more general classes: NUMERIC, introducing the basic arithmetic operations such as "+", "–" and "✳", and COMPARABLE, introducing comparison operations such as "<". As an example of genericity, we can define a generic class MATRIX whose generic parameter represents the type of matrix elements, so that instances of MATRIX [INTEGER] represent matrices of integers, instances of MATRIX [REAL] represent matrices of reals and so on. As an example of combining genericity with inheritance, the preceding definitions also allow us to use the type MATRIX [NUMERIC], whose instances represent matrices containing objects of type INTEGER as well as objects of type REAL and objects of any new type T defined by a software developer so as to inherit from NUMERIC. With a good implementation, we do not need to fear any negative consequence from the decision to define all types from classes. Nothing prevents a compiler from having special knowledge about the basic classes; the code it generates for operations on values of types such as INTEGER and BOOLEAN can then be just as efficient as if these were built-in types in the language. Object rule Every object is an instance of some class. The mathematical axioms defining integers are known as Peano’s axioms
172 THE STATIC STRUCTURE:CLASSES $7.5 Reaching the goal of a fully consistent and uniform type system requires the combination of several important O-O techniques,to be seen only later:expanded classes, to ensure proper representation of simple values;infix and prefix operators,to enable usual arithmetic syntax (such as a b or-a rather than the more cumbersome a.less than(b)or a.negated);constrained genericity,needed to define classes which may be adapted to various types with specific operations,for example a class MATR/Y that can represent matrices of integers as well as matrices of elements of other numeric types. 7.5 A SIMPLE CLASS Let us now see what classes look like by studying a simple but typical example,which shows some of the fundamental properties applicable to almost all classes. The features The example is the notion ofpoint,as it could appear in a two-dimensional graphics system A point and its coordinates To characterize type POINT as an abstract data type,we would need the four query functions x,y,p,0.(The names of the last two will be spelled out as rho and theta in software texts.)Function x gives the abscissa of a point (horizontal coordinate),y its ordinate(vertical coordinate),p its distance to the origin,0 the angle to the horizontal axis. The values ofx and y for a point are called its cartesian coordinates,those of p and e its polar coordinates.Another useful query function is distance,which will yield the distance between two points. Then the ADT specification would list commands such as translate (to move a point The name translate by a given horizontal and vertical displacement),rotate (to rotate the point by a certain refers to the "trans- angle,around the origin)and scale (to bring the point closer to or further from the origin lation"operation of geometry. by a certain factor). It is not difficult to write the full ADT specification including these functions and some of the associated axioms.For example,two of the function signatures will be x:POINT-→REAL translate:POINT X REAL×REAL→POINT and one of the axioms will be(for any point p and any reals a,b): x (translate (pl,a,b))=x(pl)+a expressing that translating a point by increases its abscissa by a
172 THE STATIC STRUCTURE: CLASSES §7.5 Reaching the goal of a fully consistent and uniform type system requires the combination of several important O-O techniques, to be seen only later: expanded classes, to ensure proper representation of simple values; infix and prefix operators, to enable usual arithmetic syntax (such as a increases its abscissa by a. A point and its coordinates θ ρ p1 x y The name translate refers to the “translation” operation of geometry
$7.5 A SIMPLE CLASS 173 Exercise E7.2,page You may wish to complete this ADT specification by yourself.The rest of this 216 discussion will assume that you have understood the ADT,whether or not you have written it formally in full,so that we can focus on its implementation-the class. Attributes and routines Any abstract data type such as POINT is characterized by a set of functions,describing the operations applicable to instances of the ADT.In classes (ADT implementations), functions will yield features-the operations applicable to instances of the class. “Function catego- We have seen that ADT functions are of three kinds:queries,commands and ries”,page134. creators.For features,we need a complementary classification,based on how each feature is implemented:by space or by time. The example of point coordinates shows the difference clearly.Two common representations are available for points:cartesian and polar.If we choose cartesian representation,each instance of the class will contain two fields representing the x and y of the corresponding point: Representing a point in cartesian coordinates (CARTESIAN_POINT) If pl is the point shown,getting its x or its y simply requires looking up the corresponding field in this structure.Getting p or 0,however,requires a computation:for p we must computey,and for e we must compute arcig (v/x)with non-zero x. If we use polar representation,the situation is reversed:p and 0 are now accessible by simple field lookup,x and y require small computations (of p cos 0 and p sin 0). Representing a point in polar rho coordinates theta (POLAR POINT) This example shows the need for two kinds of feature: Some features will be represented by space,that is to say by associating a certain piece of information with every instance of the class.They will be called attributes. For points,x and y are attributes in cartesian representation;rho and theta are attributes in polar representation
§7.5 A SIMPLE CLASS 173 You may wish to complete this ADT specification by yourself. The rest of this discussion will assume that you have understood the ADT, whether or not you have written it formally in full, so that we can focus on its implementation — the class. Attributes and routines Any abstract data type such as POINT is characterized by a set of functions, describing the operations applicable to instances of the ADT. In classes (ADT implementations), functions will yield features — the operations applicable to instances of the class. We have seen that ADT functions are of three kinds: queries, commands and creators. For features, we need a complementary classification, based on how each feature is implemented: by space or by time. The example of point coordinates shows the difference clearly. Two common representations are available for points: cartesian and polar. If we choose cartesian representation, each instance of the class will contain two fields representing the x and y of the corresponding point: If p1 is the point shown, getting its x or its y simply requires looking up the corresponding field in this structure. Getting ρ or θ, however, requires a computation: for ρ we must compute , and for θ we must compute arctg (y/x) with non-zero x. If we use polar representation, the situation is reversed: ρ and θ are now accessible by simple field lookup, x and y require small computations (of ρ cos θ and ρ sin θ). This example shows the need for two kinds of feature: • Some features will be represented by space, that is to say by associating a certain piece of information with every instance of the class. They will be called attributes. For points, x and y are attributes in cartesian representation; rho and theta are attributes in polar representation. Exercise E7.2, page 216. “Function categories”, page 134. Representing a point in cartesian coordinates x y (CARTESIAN_POINT) x 2 y 2 + Representing a point in polar coordinates rho theta (POLAR_POINT)
174 THE STATIC STRUCTURE:CLASSES $7.5 Some features will be represented by time,that is to say by defining a certain computation (an algorithm)applicable to all instances of the class.They will be called routines.For points,rho and theta are routines in cartesian representation;x and y are routines in polar representation. A further distinction affects routines (the second of these categories).Some routines will return a result,they are called functions.Herex andy in polar representation,as well as rho and theta in cartesian representation,are functions since they return a result,of type REAL.Routines which do not return a result correspond to the commands of an ADT specification and are called procedures.For example the class PO/NT will include procedures translate,rotate and scale. Be sure not to confuse the use of"function"to denote result-returning routines in classes with the earlier use of this word to denote the mathematical specifications of operations in abstract data types.This conflict is unfortunate,but follows from well-established usage of the word in both the mathematics and software fields. The following tree helps visualize this classification of features: Feature Feature classification, No result:Command Returns result:Ouery by role Arguments, No argument Procedure Computation, Memory Function Function Attribute ROUTINE This is an extemal classification,in which the principal question is how a feature will look to its clients (its users). We can also take a more internal view,using as primary criterion how each feature is implemented in the class,and leading to a different classification:
174 THE STATIC STRUCTURE: CLASSES §7.5 • Some features will be represented by time, that is to say by defining a certain computation (an algorithm) applicable to all instances of the class. They will be called routines. For points, rho and theta are routines in cartesian representation; x and y are routines in polar representation. A further distinction affects routines (the second of these categories). Some routines will return a result; they are called functions. Here x and y in polar representation, as well as rho and theta in cartesian representation, are functions since they return a result, of type REAL. Routines which do not return a result correspond to the commands of an ADT specification and are called procedures. For example the class POINT will include procedures translate, rotate and scale. Be sure not to confuse the use of “function” to denote result-returning routines in classes with the earlier use of this word to denote the mathematical specifications of operations in abstract data types. This conflict is unfortunate, but follows from well-established usage of the word in both the mathematics and software fields. The following tree helps visualize this classification of features: This is an external classification, in which the principal question is how a feature will look to its clients (its users). We can also take a more internal view, using as primary criterion how each feature is implemented in the class, and leading to a different classification: Feature classification, by role Procedure Function Function Attribute No result: Command Returns result: Query Arguments No argument Computation Memory Feature ROUTINE