Java設計模式之--外觀模式(facade pattern)

概念:

外觀模式(Facade),爲一套繁雜的子系統中的一組接口提供一個一致的界面,定義一個高層接口,這個接口使得這一子系統更加容易使用。其應用場景

1.爲一個複雜子系統提供一個簡單接口。

2.提高子系統的獨立性,降低耦合度

3.在層次化結構中,可以使用Facade模式定義系統中每一層的入口。

例子:

將基目錄下source文件中的字串讀取出,然後md5加密,再將加密的結果,輸出到目標文件

類圖:



FileRead class:

public class FileRead {
    private static String TAG = "FileRead";

    public String read(String fileName) {
        StringBuilder stringBuilder = new StringBuilder();
        File psicacheFile = new File(fileName);
        if (!psicacheFile.exists()) {
            Log.d(TAG, String.format("File:%s does not exists!",fileName));
        } else {
            try {
                FileReader fr = new FileReader(fileName);
                BufferedReader br = new BufferedReader(fr);
                String s = br.readLine();
                while (s != null) {
                    stringBuilder.append(s);
                    s = br.readLine();
                }
                br.close();
                fr.close();
            } catch (IOException ioe) {
                Log.v(TAG, ioe.toString());
            }
        }
        Log.d(TAG, String.format("FileRead String: %s", stringBuilder));
        return stringBuilder.toString();
    }
}
Encryptor加密類:

public class Encryptor {
    public final String MD5(String s) {
        char hexDigits[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};
        try {
            byte[] btInput = s.getBytes();
            MessageDigest mdInst = MessageDigest.getInstance("MD5");
            // 使用指定的字節更新摘要
            mdInst.update(btInput);
            // 獲得密文
            byte[] md = mdInst.digest();
            // 把密文轉換成十六進制的字符串形式
            int j = md.length;
            char str[] = new char[j * 2];
            int k = 0;
            for (int i = 0; i < j; i++) {
                byte byte0 = md[i];
                str[k++] = hexDigits[byte0 >>> 4 & 0xf];
                str[k++] = hexDigits[byte0 & 0xf];
            }
            return new String(str);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }
}
FileWrite class:

public class FileWrite {
    private static String TAG = "FileWrite";
    public void write(String fileName,String string){
        File psicacheFile = new File(fileName);
        if (!psicacheFile.exists()) {
            Log.d(TAG, String.format("File:%s does not exists!",fileName));
            try {
                psicacheFile.createNewFile();
                Log.d(TAG, String.format("File:%s create done!",fileName));
            } catch (IOException ioe) {
                Log.v(TAG, ioe.toString());
            }
        }
        if (psicacheFile.exists()) {
            try {
                FileWriter fw = new FileWriter(fileName);
                BufferedWriter writer = new BufferedWriter(fw);
                writer.write(string);
                writer.close();
                fw.close();
                Log.d(TAG, String.format("File:%s write in %s",fileName,string));
            } catch (IOException ioe) {
                Log.v(TAG, ioe.toString());
            }
        }
    }
}

Encryptable
public interface Encryptable {
    public void encrypt(String sourcefile, String outfile);
}

EncryptFacade外觀類:

public class EncryptFacade implements Encryptable {
    private FileRead fileRead;
    private Encryptor encryptor;
    private FileWrite fileWrite;

    @Override
    public void encrypt(String sourcefile, String outfile) {
        if (null != fileRead && null != encryptor && null != fileWrite) {
            fileWrite.write(outfile,  encryptor.MD5(fileRead.read(sourcefile)));
        }
    }

    public EncryptFacade() {
        fileRead = new FileRead();
        encryptor = new Encryptor();
        fileWrite = new FileWrite();
    }
}

測試類

public class WorkClass {
    public void test() {
        
        Encryptable encryptFacade= new EncryptFacade();
encryptFacade.encrypt("/sdcard/source.txt","/sdcard/out.txt"); }}

測試結果:

14:56:18.155 23149-23149/com.example.qinghua_liu.myapplication D/FileRead: FileRead String:facade design
 14:56:18.155 23149-23149/com.example.qinghua_liu.myapplication D/Encryptor: Encryptor MD5 facade design to 696A9711DC2670D3293E98087F94CACE
14:56:18.157 23149-23149/com.example.qinghua_liu.myapplication D/FileWrite: File:/sdcard/out.txt does not exists!
14:56:18.159 23149-23149/com.example.qinghua_liu.myapplication D/FileWrite: File:/sdcard/out.txt create done!
14:56:18.162 23149-23149/com.example.qinghua_liu.myapplication D/FileWrite: File:/sdcard/out.txt write in 696A9711DC2670D3293E98087F94CACE

結語:

外觀模式是爲了解決子系統中類與類之間的依賴關係的,像spring一樣,可以將類和類之間的關係配置到配置文件中,而外觀模式就是將他們的關係放在一個Facade類中,降低了類類之間的耦合度。如果我們沒有EncryptFacade類,那麼,FileReadFileWriteEncryptor他們之間將會相互持有實例,產生關係,這樣會造成嚴重的依賴,修改一個類,可能會帶來其他類的修改,這不是我們想要看到的,有了EncryptFacade類,他們之間的關係被放在了EncryptFacade類裏,這樣就起到了解耦的作用,這也是外觀模式的意義。


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章