try {
m.set(args[currentArgument]);
} catch (ArrayIndexOutOfBoundsException e) {
errorCode = ErrorCode.MISSING_STRING;
throw new ArgsException();
}
}
Я вплотную подошел к удалению трех старых объектов Map. Прежде всего было необходимо привести функцию getBoolean:
public boolean getBoolean(char arg) {
Args.ArgumentMarshaler am = booleanArgs.get(arg);
return am != null && (Boolean) am.get();
}
к следующему виду:
public boolean getBoolean(char arg) {
Args.ArgumentMarshaler am = marshalers.get(arg);
boolean b = false;
try {
b = am != null && (Boolean) am.get();
} catch (ClassCastException e) {
b = false;
}
return b;
}
Возможно, последнее изменение вас удивило. Почему я вдруг решил обрабатывать ClassCastException? Дело в том, что наряду с набором модульных тестов у меня был отдельный набор приемочных тестов, написанных для FitNesse. Оказалось, что тесты FitNesse проверяли, что при вызове getBoolean для аргумента с типом, отличным от Boolean, возвращается false. Модульные тесты этого не делали. До этого момента я запускал только модульные тесты[69].
Последнее изменение позволило исключить еще одну точку использования объекта Map для типа Boolean:
private void parseBooleanSchemaElement(char elementId) {
ArgumentMarshaler m = new BooleanArgumentMarshaler();
booleanArgs.put(elementId, m);
marshalers.put(elementId, m);
}
Теперь объект Map для типа Boolean можно было удалить:
public class Args {
...
private Map
new HashMap
private Map
new HashMap
private Map
new HashMap
private Map
new HashMap
...
Далее я проделал аналогичную процедуру для аргументов String и Integer и немного подчистил код:
private void parseBooleanSchemaElement(char elementId) {
marshalers.put(elementId, new BooleanArgumentMarshaler());
}
private void parseIntegerSchemaElement(char elementId) {
marshalers.put(elementId, new IntegerArgumentMarshaler());
}
private void parseStringSchemaElement(char elementId) {
marshalers.put(elementId, new StringArgumentMarshaler());
}
...
public String getString(char arg) {
Args.ArgumentMarshaler am = marshalers.get(arg);
try {
return am == null ? "" : (String) am.get();
} catch (ClassCastException e) {
return "";
}
}
...
public class Args {
...
private Map
new HashMap
private Map
new HashMap
private Map
new HashMap
...
Затем я подставил в parseSchemaElement код трех методов parse, сократившихся до одной команды:
private void parseSchemaElement(String element) throws ParseException {
char elementId = element.charAt(0);
String elementTail = element.substring(1);
validateSchemaElementId(elementId);
if (isBooleanSchemaElement(elementTail))
marshalers.put(elementId, new BooleanArgumentMarshaler());
else if (isStringSchemaElement(elementTail))
marshalers.put(elementId, new StringArgumentMarshaler());
else if (isIntegerSchemaElement(elementTail)) {
marshalers.put(elementId, new IntegerArgumentMarshaler());
} else {
throw new ParseException(String.format(