420 likes | 842 Views
Prototype Pattern. Make new instances by copying existing instances In Java, this means use the clone() method You are passed an object as a template to create a new object. Hides the complexities of creating new instances
E N D
Prototype Pattern • Make new instances by copying existing instances • In Java, this means use the clone() method • You are passed an object as a template to create a new object. • Hides the complexities of creating new instances • Provides an option for the client to generate objects whose type is not known • just the interface is known • In some cases, copying an object may be more efficient than creating new ones • Why? Programming Design Patterns
Prototype Pattern (2) • As the implementation details of the object are not known, creating a new instance and copying its data (which may not be accessible) is not possible • Solution: ask the object itself to give you a copy • Implemented using Cloneable interface in Java public class CloneObject implements Cloneable { public Object clone() { return super.clone(); } } • clone() in java.lang.Object is protected. • Cloneable is an empty interface. Why? Programming Design Patterns
Prototype Pattern (3) • Cloneable is an empty interface • It acts as a tag to indicate that you *really* want an instance of the class to be cloned. • If “implement Cloneable” is not used, super.clone() will throw CloneNotSupported Exception. • Clone() performs a shallow copy • Copies the values of the fields in the object • does not copy the objects pointed to • Cloned objects and original object will have instance variables pointing to the same objects Programming Design Patterns
Prototype Pattern (4) • Simple cloning example (adapted from jguru.com) CopyMeInterface thing = new CopyMe(); // write code to clone thing CopyMeInterface anotherThing = (CopyMeInterface)thing.clone(); Programming Design Patterns
Prototype Pattern (5) public interface Customer extends Cloneable { public Object clone(); public String getName() {…} public String setName() {…} } // Note that this method does not know what type of customer // it is storing public void storeCustomer(Customer customer) { // ADD MISSING CODE TO CREATE copy dataStore.put(copy); } Programming Design Patterns
Prototype Pattern (5) public interface Customer extends Cloneable { public Object clone(); public String getName() {…} public String setName() {…} } // Note that this method does not know what type of customer // it is storing public void storeCustomer(Customer customer) { Customer copy = (Customer) customer.clone(); dataStore.put(copy); } Programming Design Patterns
Prototype Pattern (6) Customer c1 = new FileBasedCustomer(…); Customer c2 = new EJBBasedCustomer(…); manager.storeCustomer(c1); manager.storeCustomer(c2); // as shown in previous slide, the method // just creates a clone and stores the object Programming Design Patterns
Prototype Pattern: pros/cons • Useful when lots of new objects need to be created in a complex class hierarchy • Making a copy of an object can sometimes be complicated • Example? Homework Programming Design Patterns
Vector, ArrayList, HashMap, • What is the difference between Vector and ArrayList? • Vector is synchronized, arraylist is not. • Vector doubles the array size by default • ArrayList increases the array size by 50% • Difference between HashMap and HashTable • HashMap is unsynchronized and permits nulls as keys • HashTable is synchronized Programming Design Patterns
Access and release of resources • Suppose you need to access a resource (File handle, for example) • How should you access it? • When should you release it? • Classwork: write code to get a handle to a file stream and then release it Programming Design Patterns
Access and Release of Resources (2) • Approach 1: Obtain and release a resource within the method void writeFileTest() { try { fos = new FileOuputStream(…); try{ printWriter= new PrintWriter(fos,…); } catch (…) { } finally { if (printWriter != null) printWriter.close(); } } catch (IOException e) {…} finally{ if (fos != null) fos.close(); } } Problem with this approach? Programming Design Patterns
Access and release of resources (3) • Problem with the previous approach? • It is cumbersome to obtain/release the resource each time it needs to be accessed. • What if you need to hold on to the resource between invocations (so that no other object has access to it), then this approach does not work. • Approach 2: • have separate open(…) and close(...) methods • Client can monopolize the resource as long as it wants (just don’t call the close(…) method Programming Design Patterns
Access and Release of Resources(5) • Approach 3: • obtain the resource when the object is instantiated • The class has a a separate close(...) method Programming Design Patterns
ClassWork • Write code for a Pizza store that has a createPizza() method with the following behavior: • if the requested style is NY and the type is cheese, it creates NYStyleCheesePizza • if the requested style is NY and the type is veggie, it creates NYStyleVeggiePizza • if the requested style is Chicago and the type is cheese, it creates ChicagoStyleCheesePizza • if the requested style is Chicago and the type is veggie, it creates ChicagoStyleVeggiePizza Programming Design Patterns
Simple coding assignment (2) • How many objects is the createPizza(…) method dependent on? • Reducing dependencies to concrete classes is a “good thing” • It is called “Dependency Inversion Principle”. Page 139. • Similar to “program to an interface, not an implementation” Programming Design Patterns
Open-Closed Design Principle • Classes should be open for extension, but closed for modification • (chapter 3, page 86) [design guideline] • Extend classes for new behavior/requirements • without modifying existing code • Code should be written so that it is resilient to change • but flexible to allow new functionalities via extensions • design guideline Programming Design Patterns
“new”: think concrete • When you use “new” a concrete object is being created • that means you are in the implementation class Fruit fruit; If (picnic) { fruit = new Apple(); } else if (exam) { fruit = new Orange(); } Programming Design Patterns
“new” and concrete classes • Decision of which class to instantiate is postponed to runtime • Typically code with “new” is not closed-for-modification • This part of the application code needs to be CHANGED for extensions • Maintenance is difficult and error-prone • How will programming to an interface fix this problem? • If code is written to an interface, then it will work with new classes implementing that interface through polymorphism. (page 111, chapter 4) • Homework • Identify the aspects of your code that vary and separate them from what stays the same • design principle Programming Design Patterns
Classwork: design orderPizza() • Design a method orderPizza() such that • it can be passed a string with the “type” of pizza (greek, cheese, etc) • Depending on the type, passed as a string, the method instantiates the right kind of pizza • The pizza then needs to be prepared(), baked(), cut(), boxed() • After that, the orderPizza() method returns the pizza Programming Design Patterns