http://www.yukun.info/blog/2009/03/java-design-pattern-simple-factory.html
このプログラムをちょっといじってみた。やったことはパターンが増える度にelse ifが増えてしまうことの解消と、思わぬ文字列が来てしまったときの対処(NullNamer)。結局、パターンが増えてしまえばそれだけaddPatternを呼び出さないといけないのは、仕方ないか。そして正規表現なんて使ってしまってるけど、区切り文字だけを渡せばすむ話だったと今気づく。あと1つのif文を消すためにクラス(NullNamer)を増やしてしまったのも考え物かも。以下ソース
public class Main{ public static void main(String[] args){ NameFactory nameFactory = new NameFactory(); Namer namer; namer = nameFactory.getNamer("String#indexOf"); printName(namer); namer = nameFactory.getNamer("ArrayList.get()"); printName(namer); namer = nameFactory.getNamer("Thread#run"); printName(namer); namer = nameFactory.getNamer("NULL"); printName(namer); } private static void printName(Namer namer){ System.out.println("Class Name:" + namer.getClassName()); System.out.println("Method Name:" + namer.getMethodName()); } }
import java.util.Map; import java.util.HashMap; import java.util.regex.Pattern; public class NameFactory{ private final Map<Pattern, Namer> namerMap; private static final NullNamer NULL_NAMER = new NullNamer("null", "null"); public NameFactory(){ namerMap = new HashMap<Pattern, Namer>(); addPattern(".+#.+", new SharpNamer()); addPattern(".+\\..+", new PeriodNamer()); } private void addPattern(String strPattern, Namer namer){ addPattern(Pattern.compile(strPattern), namer); } private void addPattern(Pattern pattern, Namer namer){ namerMap.put(pattern, namer); } public Namer getNamer(String input){ for(Pattern pattern : namerMap.keySet()){ if(pattern.matcher(input).matches()){ Namer namer = namerMap.get(pattern); namer.setInput(input); return namer; } } return NULL_NAMER; } }
public abstract class Namer{ protected String className; protected String methodName; public final String getClassName(){ return className; } public final String getMethodName(){ return methodName; } public abstract void setInput(String input); }
public class NullNamer extends Namer{ public NullNamer(String className, String methodName){ this.className = className; this.methodName = methodName; } @Override public void setInput(String input){} }
public class PeriodNamer extends Namer{ // 「.」で名前を区切る @Override public void setInput(String str){ int index = str.lastIndexOf("."); //すでに正規表現でチェック済みなのでif文はいらない className = str.substring(0, index); methodName = str.substring(index + 1); } }
public class SharpNamer extends Namer{ // 「#」で名前を区切る @Override public void setInput(String str){ int index = str.lastIndexOf("#"); //すでに正規表現でチェック済みなのでif文はいらない className = str.substring(0, index); methodName = str.substring(index + 1); } }