目录
1.Facade模式
1.1 作用
使用Facade模式可以为互相关联在一起的错综复杂的类整理出高层接口API, 其中的Facade角色可以让系统对外只有一个简单的接口API, 而且Facade角色还会考虑到系统内部各个类之间的责任关系和依赖关系, 按照正确的顺序调用各个类.
1.2 示例程序
实现一个用于从邮件地址中获取用户名字的数据库类, 一个用于编写HTML文件的类. 数据库文件使用一个maildata.txt简单代替:
hyuki@hyuki.com=Hiroshi Yuki hanako@hyuki.com=Hanako Sato tomura@hyuki.com=Tomura mamoru@hyuki.com=Mamoru Takahashi
1.2.1 示例程序类图
1.2.2 Database类
public class Database {
private Database(){//防止外部new出Database实例,使用private修饰
}
public static Properties getProperties(String dbname) {//读取文件获取Properties对象
String filename = dbname + ".txt";
Properties prop = new Properties();
try {
prop.load(new FileInputStream(filename));
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return prop;
}
}
1.2.3 HtmlWriter类
//编写简单的页面,并输出HTML文件
public class HtmlWriter {
private Writer writer;
public HtmlWriter(Writer writer) {
this.writer = writer;
}
public void title(String title) throws IOException {//输出标题
writer.write("<html>");
writer.write("<head>");
writer.write("<title>" + title + "</title>");
writer.write("</head>");
writer.write("<body>\n");
writer.write("<h1>" + title + "</h1>\n");
}
public void paragraph(String msg) throws IOException {//输出段落
writer.write("<p>" + msg + "</p>\n");
}
public void link(String href,String caption) throws IOException {//输出超链接
paragraph("<a href=\"" + href + "\">" + caption + "</a>");
}
public void mailto(String mailaddr,String username) throws IOException {//输出邮件地址
link("mailto:" + mailaddr,username);
}
public void close() throws IOException{
writer.write("</body>");
writer.write("</html>\n");
writer.close();
}
}
1.2.4 PageMaker类
//供外部使用的类
public class PageMaker {
private PageMaker(){//防止外部new出Database实例,使用private修饰
}
public static void makeWelcomePage(String mailaddr,String filename) {//向外提供的唯一接口
try {
Properties mailprop = Database.getProperties("maildata");
String username = mailprop.getProperty(mailaddr);
HtmlWriter writer = new HtmlWriter(new FileWriter(filename));
//内部决定了调用的顺序
writer.title("Welcome to " + username + "\'s page!");
writer.paragraph("欢迎来到" + username + "的主页");
writer.paragraph("等着你的邮件哦!");
writer.mailto(mailaddr,username);
writer.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
1.2.5 Main类
public class Main {
public static void main(String[] args) {
PageMaker.makeWelcomePage("hyuki@hyuki.com","welcome.html");
}
}
打开welcome.html文件:
1.3 Facade模式中的角色
- Facade(窗口): 该角色是代表构成系统的许多其他角色的"简单窗口", Facade角色向系统外部提供高层接口API. 上述的PageMaker类.
- 构成系统的许多其他角色: 这些角色各自完成自己的工作, 它们不知道Facade角色, Facade角色调用其他角色进行工作, 但其他角色不会调用Facade角色.
- Client(请求者): 该角色负责调用Facade角色.
1.4 其他特点
- Facade模式的重点是对于外界使用者来说, 接口API减少了, 也意味着程序与外部的关联关系弱化了, 这样更容易使我们的包(类的集合)作为组件复用.
- 可以递归地使用Facade模式. 假设现在有几个持有Facade角色的类的集合, 我们可以通过整个这几个集合来引入新的Facade角色.
根据图解设计模式书籍进行整理.