???????洴?????????????PetCreator????????????????arrayList()?????????????????Pet????????????????????????????????newInstance()????????????Class??????????????????????????????????????????new Dog().getClass().newInstance()?????new Dog()??????
public abstract class PetCreator {
private Random rand = new Random(47);
// The List of the different getTypes of Pet to create:
public abstract List<Class<? extends Pet>> getTypes();
public Pet randomPet() {
// Create one random Pet
int n = rand.nextInt(getTypes().size());
try {
return getTypes().get(n).newInstance();
} catch (InstantiationException e) {
throw new RuntimeException(e);
} catch (IllegalAccessException e) {
throw new RuntimeException(e);
}
}
public Pet[] createArray(int size) {
Pet[] result = new Pet[size];
for (int i = 0; i < size; i++) {
result[i] = randomPet();
}
return result;
}
public ArrayList<Pet> arrayList(int size) {
ArrayList<Pet> result = new ArrayList<Pet>();
Collections.addAll(result?? createArray(size));
return result;
}
}
????????????????????????????????????????????????????????????У?????????????????????allTypes??types??????allTypes?а??????????????????????????????????????????????????????????Mutt??EgypianMau?????????????????new????????????types?????????????????????????????getTypes()???????types??????????????????
????public class LiteralPetCreator extends PetCreator {
????@SuppressWarnings("unchecked")
????public static final List<Class<? extends Pet>> allTypes = Collections.unmodifiableList(
????Arrays.asList(Pet.class?? Dog.class?? Cat.class?? Mutt.class?? EgyptianMau.class));
????private static final List<Class<? extends Pet>> types = allTypes.subList(
????allTypes.indexOf(Mutt.class)?? allTypes.size());
????public List<Class<? extends Pet>> getTypes() {
????return types;
????}
????}
?????????????????????????????????????????????Pet???????TypeCounter?????????isAssignalbeFrom()?????????????ж?????????????????????????????????????getSuperclass()???????????????????????????
public class TypeCounter extends HashMap<Class<?>?? Integer> {
private Class<?> baseType;
public TypeCounter(Class<?> baseType) {
this.baseType = baseType;
}
public void count(Object obj) {
Class<?> type = obj.getClass();
if (!baseType.isAssignableFrom(type)) {
throw new RuntimeException(
obj + " incorrect type " + type + "?? should be type or subtype of " + baseType);
}
countClass(type);
}
private void countClass(Class<?> type) {
Integer quantity = get(type);
put(type?? quantity == null ? 1 : quantity + 1);
Class<?> superClass = type.getSuperclass();
if (superClass != null && baseType.isAssignableFrom(superClass)) {
countClass(superClass);
}
}
@Override
public String toString() {
StringBuilder result = new StringBuilder("{");
for (Map.Entry<Class<?>?? Integer> pair : entrySet()) {
result.append(pair.getKey().getSimpleName());
result.append("=");
result.append(pair.getValue());
result.append("?? ");
}
result.delete(result.length() - 2?? result.length());
result.append("} ");
return result.toString();
}
}