Instead of instantiating from a class, create another instance from one instance. Create a new instance based on the prototype instance.
Define a method for copying an instance and creating a new instance.
package framework;
public interface Product extends Cloneable {
//A method for "using". It's up to the subclass implementation to use it but what it means
public abstract void use(String s);
//Duplicate the instance
public abstract Product createClone();
}
Actually implement the method that copies the instance and creates a new instance.
import framework.Product;
public class MessageBox implements Product {
private char decochar;
public MessageBox(char decochar) {
this.decochar = decochar;
}
@Override
public void use(String s) {
int length = s.getBytes().length;
for (int i = 0; i < length + 4; i++) {
System.out.print(decochar);
}
System.out.println("");
System.out.println(decochar + " " + s + " " + decochar);
for (int i = 0; i < length + 4; i++) {
System.out.print(decochar);
}
System.out.println("");
}
@Override
public Product createClone() {
Product p = null;
try {
p = (Product)clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
return p;
}
}
import framework.Product;
public class UnderlinePen implements Product {
private char ulchar;
public UnderlinePen(char ulchar) {
this.ulchar = ulchar;
}
@Override
public void use(String s) {
int length = s.getBytes().length;
System.out.println("\"" + s + "\"");
System.out.print(" ");
for (int i = 0; i < length; i++) {
System.out.print(ulchar);
}
System.out.println("");
}
@Override
public Product createClone() {
Product p = null;
try {
p = (Product)clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
return p;
}
}
Create a new instance using the method that copies the instance.
package framework;
import java.util.HashMap;
/**
*A class that replicates an instance using the Product interface
*/
public class Manager {
private HashMap<String, Product> showcase = new HashMap<>();
public void register(String name, Product proto) {
showcase.put(name, proto);
}
public Product create(String protoname) {
Product p = showcase.get(protoname);
return p.createClone();
}
}
import framework.Manager;
import framework.Product;
public class Main {
public static void main(String[] args) {
//Preparation
Manager manager = new Manager();
UnderlinePen upen = new UnderlinePen('~');
MessageBox mbox = new MessageBox('*');
MessageBox sbox = new MessageBox('/');
manager.register("strong message", upen);
manager.register("warning box", mbox);
manager.register("slash box", sbox);
//Generate
Product p1 = manager.create("strong message");
p1.use("Hello, world");
Product p2 = manager.create("warning box");
p2.use("Hello, world");
Product p3 = manager.create("slash box");
p3.use("Hello, world");
}
}
// "Hello, world"
// ~~~~~~~~~~~~
// ****************
// * Hello, world *
// ****************
// ////////////////
// / Hello, world /
// ////////////////
If you want to create an instance, you can simply use new Something (), but it is effective in the following cases.
Three models have appeared in this program. Underlining a string with'~' Use'*' to frame a string Use'/' to frame a string
Since this example is simple, there are three templates, but if you feel like it, you can make as many types as you like. If you put them all in separate classes, the number of classes will be too large and it will be difficult to manage the source.
If you want to create the same instance that represents the shape created by the user, it is easier to copy the instance instead of using the class.
In the sample program, the part that copies the instance (clone) is confined in the framework package. In the create method of the Manager class, a character string such as "strong message" is given as the name for instantiation instead of the class name. It can be said that this makes the form of new Something (), which is the mechanism of instantiation provided by the Java language, more general, and separates the framework from the binding of class names.
Recommended Posts