定义:
将对象以树形结构组织起来,以达成"部分-整体"的层次结构,使得客户端对单个对象和组合对象的使用具有一致性。
组合模式其实对是我们数据结构中的树形结构。一颗树下面还有子树,将要进行调用方法时,将会进行深度遍历.
Composite好处:
1.使客户端调用简单,客户端可以一致的使用组合结构或其中单个对象,用户就不必关系自己处理的是单个对象还是整个组合结构,这就简化了客户端代码。
2.更容易在组合体内加入对象部件. 客户端不必因为加入了新的对象部件而更改代码。
例子:
Junit的运行方法机制就是采用组合模式进行,为了达到自动化测试目的,Junit中定义了两个概念,TestCase和TestSute,TestCase是编写的测试类,而TestSuite是一个不同的TestCase的集合,当然这个集合里也可以包含TestSuite元素,这样运行一个TestSuite会将其包含的TestCase全部运行。然而在真实运行机制中是不需要关心这两个类的,我们只关心测试结果,这就是为什么Junit使用组合模式的原因。
Junit为了采用组合模式将TestCase和TestSuite统一起来,创建了一个Test接口来扮演抽象角色,这样原来TestCase扮演组合模式中树叶构件角色 ,TestSuite是树枝构件角色。
有关代码如下:
Test接口
public interface Test {
/**
* Counts the number of test cases that will be run by this test.
*/
public abstract int countTestCases();
/**
* Runs a test and collects its result in a TestResult instance.
*/
public abstract void run(TestResult result);
}
TestSuite实现了Test接口
/**
* Runs the tests and collects their result in a TestResult.
*/
public void run(TestResult result) {
for (Enumeration e= tests(); e.hasMoreElements(); ) {
if (result.shouldStop() )
break;
Test test= (Test)e.nextElement();
runTest(test, result);
}
}
//此方法继续调用上面的方法进行递归
public void runTest(Test test, TestResult result) {
test.run(result);
}
TestCase
/**
* Counts the number of test cases executed by run(TestResult result).
*/
public int countTestCases() {
return 1;
}
/**
* Creates a default TestResult object
*
* @see TestResult
*/
protected TestResult createResult() {
return new TestResult();
}
/**
* A convenience method to run this test, collecting the results with a
* default TestResult object.
*
* @see TestResult
*/
public TestResult run() {
TestResult result= createResult();
run(result);
return result;
}
/**
* Runs the test case and collects the results in TestResult.
*/
public void run(TestResult result) {
result.run(this);
}
以上这一点代码并不能够让我们知道junit的真正内部实现,个人也不是了解的非常透彻,但以上代码可以说明一个问题,组合模式就是采用类似树一样的递归方式。