Junit是如何使用适配器模式的呢?概念上可以理解,但是实际上看了代码之后才更有意思。
TestCase有一个参数叫fname。TestSuit使用组合模式将多个TestCase包括进来,包括的方法有三:
创建空的TestSuite,将需要的TestCase的实例通过addTest方法加入,这些TestCase需要指明testXXX的方法名。
要么直接传这个TestCase的class类型。
最后是传一个class类型的数组进来。
不管哪种方法,最后其实都走的是第一种方法,后面的两种方法只是类似重载构造方法罢了。在TestSuite里有个Vector,是用来存多个TestCase的实例的。
当以第一种形式,创建空的TestSuite,再把包含testXXX方法名字的TestCase实例直接放放入Vector中。
第二种形式,以class类型传入,首先通过class的自带方法getName解析class的类型,并把它赋给fName。然后解析class类型,得到所有的Junit认可的testXXX方法,将这些方法名,通过TestCase的带fName参数的构造函数生成一个个的TestCase实例,将这些实例放入Vector。
可以看源码,addTestMethod是加入TestMethod的方法,另外它调用createTest(),这个方法创建不同的实例。
private void addTestMethod(Method m, Vector names, Class theClass) { String name= m.getName(); if (names.contains(name)) return; if (! isPublicTestMethod(m)) { if (isTestMethod(m)) addTest(warning("Test method isn't public: "+m.getName())); return; } names.addElement(name); addTest(createTest(theClass, name)); } static public Test createTest(Class theClass, String name) { Constructor constructor; try { constructor= getTestConstructor(theClass); } catch (NoSuchMethodException e) { return warning("Class "+theClass.getName()+" has no public constructor TestCase(String name) or TestCase()"); } Object test; try { if (constructor.getParameterTypes().length == 0) { test= constructor.newInstance(new Object[0]); if (test instanceof TestCase) ((TestCase) test).setName(name); } else { test= constructor.newInstance(new Object[]{name}); } } catch (InstantiationException e) { return(warning("Cannot instantiate test case: "+name+" ("+exceptionToString(e)+")")); } catch (InvocationTargetException e) { return(warning("Exception in constructor: "+name+" ("+exceptionToString(e.getTargetException())+")")); } catch (IllegalAccessException e) { return(warning("Cannot access test case: "+name+" ("+exceptionToString(e)+")")); } return (Test) test; }
第三种形式,只是多次调用第二种形式的结果。