1 / 30

SYSC 3100 System Analysis and Design

SYSC 3100 System Analysis and Design. Class Diagrams Generalization hierarchies substitutability. Objectives . Generalization: When to use it and when not to. Identify the types of generalization: Interface (the good) Implementation (the potentially bad) Extension

moesha
Download Presentation

SYSC 3100 System Analysis and Design

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. SYSC 3100 System Analysis and Design Class Diagrams Generalization hierarchies substitutability SYSC3100 - System Analysis and Design

  2. Objectives • Generalization: When to use it and when not to. • Identify the types of generalization: • Interface (the good) • Implementation (the potentially bad) • Extension • Restriction (the definitely bad!) • Convenience (the ugly) • Use of delegation versus inheritance. (you have seen this before). • An introduction to the Liskov Substitution Principle. This lecture is probably the most important one of all when it comes to good Object-Oriented design!!! SYSC3100 - System Analysis and Design

  3. Introduction • Generalization is a relationship between a more general element and a more specific element, where the more specific element is entirely consistent with the more general element but contains more information. • The two elements obey the substitutability principle – we can use the more specific element where the more general element is expected without breaking the system. • Generalization is a much stronger type of relationship than association. • Generalization implies the very highest level of dependency and therefore coupling between two elements. SYSC3100 - System Analysis and Design

  4. Inheritance and generalization • Generalization • Useful and powerful concept but many problems due to intricacies of inheritance • States that the interface of the subclass must include all (public and protected) properties of the superclass • Inheritance is “the mechanism by which more specific elements incorporate structure and behavior defined by more general elements” • Inheritance is not generalization – the former is the programming language mechanism through which proper generalization can be implemented. • Benefits of generalization arise from the substitutability principle • Subclass object can be used in place of a superclass object in any part of the code where the superclass object is accessed • However, and unfortunately, the inheritance mechanism may be used in a way that defeats the benefits of the substitutability principle SYSC3100 - System Analysis and Design

  5. Inheritance vs encapsulation • Encapsulation • Demands that object's attributes be only accessible through the operations in the object’s interface • Is orthogonal to inheritance • Inheritance compromises encapsulation by allowing subclasses to directly access protected attributes • This can lead to serious problems, i.e., no substitutability SYSC3100 - System Analysis and Design

  6. Overriding and callbacks • Subclass can inherit the • Method signature and implementation and introduces no changes to the implementation • Implementation and include it (call it) in its own method with the same signature • Implementation and then completely override it with a new implementation with the same signature • Implementation that is empty (i.e. the method declaration is empty) and then provide the implementation for the method • Method signature only and then provide the implementation for the method SYSC3100 - System Analysis and Design

  7. Interface inheritance • Interface inheritance: subtyping, type inheritance • This is a “harmless” form of inheritance • A subclass inherits attribute types and operation signatures (operation names plus formal arguments) • A subclass is said to support a superclass interface • The implementation of inherited operations is deferred until later • The interfaces are normally declared through an abstract class • We can say – with one proviso – that an interface is an abstract class • The proviso is that an abstract class can provide partial implementations for some operations whereas a pure interface defers the definition of all operations SYSC3100 - System Analysis and Design

  8. Interface inheritance Computer - computer_name : String + getConf() ConfiguredComputer StandardComputer - configured_price : Currency - standard_price : Currency + getConf() + getConf() SYSC3100 - System Analysis and Design

  9. Realization relationship An alternative way of representing the interface inheritance - with a “lollypop” symbol to indicate the supported interface. The “lollypop” relationship from a subclass (concrete class) to an abstract class is formally called the realization relationship. SYSC3100 - System Analysis and Design

  10. Implementation inheritance • Generalization can be used (deliberately or not) to imply code reuse and it is then realized by an implementation inheritance • A very powerful, sometimes dangerously powerful, interpretation of generalization • It is also the “default” interpretation of generalization • Combines the superclass properties in the subclasses and allows overriding them with new implementations, when necessary • Allows sharing of property descriptions, code reuse, and polymorphism SYSC3100 - System Analysis and Design

  11. Extension inheritance • Inheritance as an incremental definition of a class • A subclass is-kind-of superclass • This is a proper use of implementation inheritance • The overriding of properties should be used with care. It should only be allowed to make properties more specific (e.g. to produce additional outputs, to make implementations of operations more efficient), not to change the meaning of a property. SYSC3100 - System Analysis and Design

  12. Restriction inheritance • Inheritance as a restriction mechanism whereby some inherited properties are suppressed in the subclass • This is a problematic use of inheritance • A superclass object can still be substituted by a subclass object provided that whoever is using the object is aware of the suppressed properties SYSC3100 - System Analysis and Design

  13. Convenience inheritance • When two or more classes have similar implementations, but there is no taxonomic relationship between the concepts represented by the classes • One class is selected arbitrarily as an ancestor of the others • This is an improper use of inheritance SYSC3100 - System Analysis and Design

  14. Convenience inheritance • When inheritance is used for the purpose of reusing code but does not implement a proper generalization • Example: Set implemented by inheriting from Hashtable • Convenience inheritance results in operations being inherited but meaningless in the context of the subclass. This is potentially dangerous as it can create confusion when one modifies or uses the subclass • Convenience inheritance should be avoided and substituted with Delegation • A class is said to delegate to another class if it implements an operation by merely resending a message to another class. SYSC3100 - System Analysis and Design

  15. Myset Example Object design model before transformation Object design model after transformation Hashtable Hashtable put(key,element) put(key,element) get(key):Object get(key):Object containsKey(key):boolean containsKey(key):boolean containsValue(element):boolean containsValue(element):boolean table 1 1 MySet MySet put(element) put(element) containsValue(element):boolean containsValue(element):boolean SYSC3100 - System Analysis and Design

  16. Myset Java Implementation /* Implementation of MySet using inheritance */ class MySet extends Hashtable { /* Constructor omitted */ MySet() { } void put(Object element) { if (!containsKey(element)){ put(element, this); } } boolean containsValue(Object element){ return containsKey(element); } /* Other methods omitted */ } /* Implementation of MySet using delegation */ class MySet { Hashtable table; MySet() { table = new Hashtable(); } void put(Object element) { if (!table.containsKey(element)){ table.put(element,this); } } boolean containsValue(Object element) { return (table.containsKey(element)); } /* Other methods omitted */ } SYSC3100 - System Analysis and Design

  17. Stack with Inheritance v. Delegation • Implementing a Stack class by reusing a LinkedList class • Our Stack class contains the following: • push() to add an object to the top of the stack • peek():Object to return the object on the top of the stack. • isEmpty():boolean to return true if there are no objects on the stack. • pop():Object to remove an object from the top of the stack and return it. • Now, the LinkedList class contains among others the following four messages that we can reuse: • addElement() which adds an object to the end of the list • lastElement():Object which returns the object at the end of the list. • numberOfElement():int which returns the number of objects in the list. • removeLastElement() which removes the object at the end of the list. SYSC3100 - System Analysis and Design

  18. Implementing the stack using inheritance • Let say we choose to make our Stack class a subclass of LinkedList as shown. Then we have the Java code: Public class Stack extends LinkedList { public void push(Object o) { addElement(o); } public Object peek() { return lastElement(); } public boolean isEmpty() { return numberOfElements() == 0; } public Object pop() { Object o = lastElement(); removeLastElement(); return o; } } We can now create a stack object and use it: Stack aStack = new Stack(); aStack.push(new Plate(“Wedgwood”)); … SYSC3100 - System Analysis and Design

  19. Stack with inheritance cont. • There is potentially serious problem with this way of implementing Stack. • Since Stack is a subclass of LinkedList, all other LinkedList messages are also available to stack objects since a subclass is expected to offer at least the same services as its superclass. • Now, the problem is that if LinkedList has messages such as firstElement that a client would still be able to use and that are inappropriate for Stack e.g. Person aPerson = new Person() aPerson.take(aStack.firstElement()); • This piece of code means that the client of aStack has just removed the element from the bottom of the stack – something that the client is not supposed to be able to do. SYSC3100 - System Analysis and Design

  20. Stack using Delegation Public class Stack { private LinkedList list; public Stack() { list = new LinkedList(); } public void push(Object o) { addElement(o); } public Object peek() { return lastElement(); } public boolean isEmpty() { return numberOfElements() == 0; } public Object pop() { Object o = lastElement(); removeLastElement(); return o; } } The following does not work : aPerson.take(aStack.firstelement()); • In this case, the behaviour of encapsulated LinkedList is used by Stack but none of the extra LinkedList behaviour is exposed to Stack clients. In other words aStackdelegates its behaviour to aLinkedList. SYSC3100 - System Analysis and Design

  21. Liskov Substitution Principle • Liskov substitution principle states that, if a client code uses the methods provided by a superclass, then developers should be able to add new subclasses without having to change the client code. • This principle defines the notions of generalization / specialization in a formal manner • Class S is correctly defined as a specialization of class T if the following is true: a client method written in terms of superclass T must be able to use instances of S without knowing whether the instances are of S or T. • S is a said to be a subtype of T • Instances of a subclass can stand for instances of a superclass without any effect on client classes • Any future extension (new subclasses) will not affect existing clients. • Any future extension (new subclasses) will not affect parent methods SYSC3100 - System Analysis and Design

  22. Lack of Substitutability class Rectangle : public Shape { private: int w, h; public: virtual void set_width(int wi) { w=wi; } virtual void set_height(int he) { h=he; } } class Square : public Rectangle { public: void set_width(int w) { Rectangle::set_height(w); Rectangle::set_width(w); } void set_height(int h) { set_width(h); } } void foo(Rectangle *r) { r->set_width(5); r->set_height(4); assert((r->get_width()*r->get_height()) ==20); } SYSC3100 - System Analysis and Design

  23. Rules • Signature Rule: The subtypes must have all the methods of the supertype, and the signatures of the subtypes’ methods must be compatible with the signatures of the corresponding supertypes methods • In Java, this is enforced as the subtype must have all the supertype methods, with identical signatures except that a subtype method can have fewer exceptions (compatibility stricter than necessary here) • Method Rule: Calls on the subtype methods must “behave like” calls to the corresponding supertype methods. • Property Rule: The subtype must preserve the invariant of the supertype. SYSC3100 - System Analysis and Design

  24. Method Rule • S is a subtype of T • If methods T::m() and S::m() (overriding) have preconditions PrC1 and PrC2, respectively, PrC1 => PrC2 • The precondition is weakened • If methods T::m() and S::m() (overriding) have postconditions PoC1 and PoC2, respectively, PoC2 => PoC1 • The postcondition is strengthened SYSC3100 - System Analysis and Design

  25. IntSet public class IntSet { private Vector els; /// the elements public IntSet() {…} // Post: Initializes this.els to be empty public void insert (int x) {…} // Post: Adds x to the elements of this public void remove (int x) {…} // Post: Remove x from the elements of this public boolean isIn (int x) {…} //Post: If x is in this returns true else returns false public int size () {…} //Post: Returns the cardinality of this public boolean subset (IntSet s) {…} //Post: Returns true if this is a subset of s else returns false } SYSC3100 - System Analysis and Design

  26. MaxIntSet public class MaxIntSet extends IntSet { private int biggest; // biggest element if set not empty public maxIntSet () {…} // call super() public max () throws EmptyException {…} // new method public void insert (int x) {…} // overrides InSet::insert() //Additional Post: update biggest with x if x > biggest public void remove (int x) {…} // overrides InSet::remove() //Additional Post: update biggest with next biggest element in this if x = biggest } SYSC3100 - System Analysis and Design

  27. Example Preconditions public class LinkedList { ... /** * Adds an element to the end of the list * * PRE: element != null * * POST: this.getLength() == old.getLength() + 1 * && this.contains(element) == true */ public void addElement(Object element) { ... } ... } public class Set extends LinkedList { ... /** * Adds element to this set, provided * element is not already in the set * * PRE: element != null * && this.contains(element) == false * * POST: this.getLength() == old.getLength() + 1 * && this.contains(element) == true */ public void addElement(Object element) { ... } ... } SYSC3100 - System Analysis and Design

  28. Properties Rule • All methods of the subtype (i2) must preserve the invariant of the supertype (i1) • The invariant of the subtype must imply the invariant of the supertype (i2 => i1) • Assume FatSet is a set of integers whose cardinality (card) is always at least 1. The constructor and remove methods ensure this. • Inv:self.card >= 1 • ThinSet is also a set of integers but can be empty and therefore cannot be a legal subtype of FatSet • Inv:self.card >= 0 SYSC3100 - System Analysis and Design

  29. InSet, MaxInSet • Invariant of IntSet, for any instance i : i.els != null and All elements of i.els are Integers and There are no duplicates in i.els • Invariant of MaxIntSet, for any instance i : Invariant of InSet and i.size > 0 and For all integers x in els, x <= i.biggest SYSC3100 - System Analysis and Design

  30. Summary • Generalization should only be used when subclassing makes sense. • All subclass objects should behave the same way as their superclass object (this is the basis of the Liskov Substitution Principle). • Beware of convenience and restriction subclassing! • Interfaces are always a good thing! • We can always make use of delegation (essentially, referencing another object via an association – this is the basis of the ‘self’ programming language.) SYSC3100 - System Analysis and Design

More Related