3 Class Specifications - Recap Contract vs. defensive programming: The contract approach simplifies class testing, but complicates interaction testing because we must ensure any sender meets preconditions. The defensive programming approach complicates both class testing (test cases must address all possible outcomes); and interaction testing (we must ensure all possible outcomes are produced and that they are properly handled by a sender).
4 Class Implementation Class implementation describes how an object represents its attributes and carries out operations. It compromises several components: A set of data values stored in data members (instance variables or variables). A set of methods (member functions in C++ or methods in Java) constitutes code that will be used to implement an algorithm that accomplishes one operation declared in the public or private class specification.
5 Class Implementation From testing perspective, potential causes of failures within class design and implementation: A class specification contains operations to construct instances. These operations may not properly initialize the attributes of the new instances. A class relies on collaboration with other classes to define its behaviors and attributes. These other classes may be implemented incorrectly. A class’ implementation “satisfies” its specification, but that is no guarantee that the specification is correct.
6 Class Implementation The implementation might not support all required operations or may incorrectly perform operations. A class specifies preconditions to each operation. The class may not provide a way for the precondition to be checked by a sender before sending a message.
7 Class Implementation The design approach used, contract or defensive, gives rise to different sets of potential problems: In contract approach we only need to test situations in which the precordinations are satisfied. In defensive programming approach we must test every possible input to determine that the outcome is handled properly.
8 Inheritance Inheritance is a relationship between classes that allows the definition of a new class based on the definition of an existing class. Inheritance is “is-a” (or “is a kind of”) relationship. Pre-existing class does not have to be modified or made aware in any way of the new class. The new class is referred to as a subclass or derived class (in C++). If a class inherits from another class, the other class is referred to as a super class or base class (in C++).
9 Inheritance The set of classes that inherit either directly or indirectly from a given class form an inheritance hierarchy. Testers care about Propagation of errors Potential for test reuse
10 Inheritance – Tester’s Perspective Provides a mechanism by which bugs can be propagated from a class to its descendents. Testing a class as it is developed eliminates faults early before they are passed on to the other classes.
11 Inheritance – Tester’s Perspective Provides a mechanism by which we can reuse test cases Reuse test cases for the super class in testing the subclass.
12 Polymorphism Polymorphism is the ability to treat an object as belonging to more than one type. Testers care about: Unanticipated interactions
13 Polymorphism Inclusion polymorphism: Inclusion polymorphism is the occurrence of different forms in the same class (dynamic binding) substitute an object whose specification matches another object’s specification for the later object in a request for an operation:
14 Polymorphism In C++: Inclusion polymorphism arises from the inheritance relationship. A derived class inherits the public interface of its base class and thus instances of the derived class can respond to the same message as the base class. In Java: Inclusion polymorphism is supported both through inheritance between classes and an implementation relationship between interfaces and classes.
15 Polymorphism – Testing Perspective Inclusion polymorphism from testing perspective: Inclusion polymorphism allows systems to be extended incrementally by adding classes rather than modifying existing ones.
16 Polymorphism – Testing Perspective Inclusion polymorphism allows any operation to have one or more parameters of a polymorphic reference. This increases the number of possible kinds of actual parameters that should be tested. A polymorphic reference is a reference variable that can refer to different types of objects at different points in time.
17 Polymorphism Parametric polymorphism is the capability to define a type in terms of one or more parameters (e.g. templates in C++) From testing perspective: If the template works for one instantiation, there is no guarantee it will work for another.
18 Development products Unified Modelling Language Developed by Grady Booch, James Rumbaugh, and Ivar Jacobson Combined Booch's O-O design, Rumbaugh's OMT, and Jacobson’s OOSE A notation for modelling
19 Development products: analysis models Two levels of analysis domain: Domain analysis: focuses on an understanding of the problem domain-that is, the general area of interest in which the problem of immediate interest lies. Application analysis: focuses on specific problem and the requirements for a solution. Analysis models: use case, class, state, sequence, and activity diagrams
20 UML diagrams Use case diagram: represents the actors and uses of the system and relationships between the uses. Class diagram: represents the individual class definitions and the relationships between classes. Package diagram: presents conceptual groupings of classes with dependencies between groups. Sequence diagrams: records the sequence of messages that represent an algorithm.
21 UML diagrams State diagram: presents different configurations of data-attribute values and the messages that transform the data from one configuration to another. Activity diagram: aggregates all possible paths through the logic of a method.
22 Development products: design models From a testing perspective, we can reuse and extend use cases developed for analysis models. Major issues: Who tests: testing can be done by developers who adopt a testing perspective. What to test: each class can be tested separately before it is used as part of the system.
23 Development products: source code When testing is done: testing can be done at any time during development. How testing is done: function-based and specification-based. How much testing is done: exhaustive testing of each software component and of a whole system is seldom practical or possible.