国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 學院 > 開發設計 > 正文

Java模式設計之單例模式(三)

2019-11-18 15:47:18
字體:
來源:轉載
供稿:網友

  一個實用的例子:屬性治理器

  什么是屬性文件

  這里給出一個讀取屬性(PRoperties) 文件的單例類,作為單例模式的一個實用的例子。屬性文件如同老式的視窗編程時的.ini 文件,用于存放系統的配置信息。配置信息在屬性文件中以屬性的方式存放,一個屬性就是兩個字符串組成的對子,其中一個字符串是鍵(key),另一個字符串是這個鍵的值(value)。

  大多數的系統都有一些配置常量,這些常量假如是存儲在程序內部的,那么每一次修改這些常量都需要重新編譯程序。將這些常量放在配置文件中,系統通過訪問這個配置文件取得配置常量,就可以通過修改配置文件而無需修改程序而達到更改系統配置的目的。系統也可以在配置文件中存儲一些工作環境信息,這樣在系統重啟時,這些工作信息可以延續到下一個運行周期中。

  假定需要讀取的屬性文件就在當前目錄中,且文件名為singleton.properties 。這個文件中有如下的一些屬性項。

  代碼清單5:屬性文件內容

node1.item1=How
node1.item2=are
node2.item1=you
node2.item2=doing
node3.item1=?
  例如,node1.item1 就是一個鍵,而How 就是這個鍵所對應的值。

  java 屬性類

  Java 提供了一個工具類,稱做屬性類,可以用來完成Java 屬性和屬性文件的操作。這個屬性類的繼續關系可以從下面的類圖中看清楚。

Java模式設計之單例模式(三)(圖一)

  屬性類提供了讀取屬性和設置屬性的各種方法。其中讀取屬性的方法有:

   .. contains(Object value) 、containsKey(Object key): 假如給定的參數或屬性要害字在屬性表中有定義,該方法返回True ,否則返回False。

   .. getProperty(String key)、getProperty(String key, String default) :根據給定的屬性要害字獲取要害字值。

   .. list(PrintStream s) 、list(PrintWriter w) :在輸出流中輸出屬性表內容。

   .. size():返回當前屬性表中定義的屬性要害字個數。

  設置屬性的方法有:

   .. put(Object key, Object value) :向屬性表中追加屬性要害字和要害字的值。

   .. remove(Object key):從屬性表中刪除要害字。

  從屬性文件加載屬性的方法為load(InputStream inStream),可以從一個輸入流中讀入一個屬性列,假如這個流是來自一個文件的話,這個方法就從文件中讀入屬性。

  將屬性存入屬性文件的方法有幾個,重要的一個是store(OutputStream out, String header) ,將當前的屬性列寫入一個輸出流,假如這個輸出流是導向一個文件的,那么這個方法就將屬性流存入文件。進入討論組討論。
為什么需要使用單例模式

  屬性是系統的一種"資源",應當避免有多余一個的對象讀取非凡是存儲屬性。此外,屬性的讀取可能會在很多地方發生,創建屬性對象的地方應當在哪里不是很清楚。換言之,屬性治理器應當自己創建自己的實例,并且自己向系統全程提供這一事例。因此,屬性文件治理器應當是一個單例模式負責。

  系統設計

  系統的核心是一個屬性治理器,也就是一個叫做ConfigManager 的類,這個類應當是一個單例類。因此,這個類應當有一個靜態工廠方法,不妨叫做getInstance(), 用于提供自己的實例。

  為簡單起見,本文在這里采取"餓漢"方式實現ConfigManager 。例子的類圖如下所示。

Java模式設計之單例模式(三)(圖二)


  本例子的源代碼如下所示。

  代碼清單6:ConfigManager 的源代碼

import java.util.Properties;
import java.io.FileInputStream;
import java.io.File;
public class ConfigManager
{
/**
* 屬性文件全名
*/
private static final String PFILE =
System.getProperty("user.dir")
+ File.Separator + "Singleton.properties";
/**
* 對應于屬性文件的文件對象變量
*/
private File m_file = null;
/**
* 屬性文件的最后修改日期
*/
private long m_lastModifiedTime = 0;
/**
* 屬性文件所對應的屬性對象變量
*/
private Properties m_props = null;
/**
* 本類可能存在的惟一的一個實例
*/
private static ConfigManager m_instance =
·234·Java 與模式
new ConfigManager();
/**
* 私有的構造子,用以保證外界無法直接實例化
*/
private ConfigManager()
{
m_file = new File(PFILE);
m_lastModifiedTime = m_file.lastModified();
if(m_lastModifiedTime == 0)
{
System.err.println(PFILE +
" file does not exist!");
}
m_props = new Properties();
try
{
m_props.load(new FileInputStream(PFILE));
}
catch(Exception e)
{
e.printStackTrace();
}
}
/**
* 靜態工廠方法
* @return 返還ConfigManager 類的單一實例
*/
synchronized public static ConfigManager
getInstance()
{
return m_instance;
}
/**
* 讀取一特定的屬性項
*
* @param name 屬性項的項名
* @param defaultVal 屬性項的默認值
* @return 屬性項的值(如此項存在), 默認值(如此項不存在)
*/
final public Object getConfigItem(
String name, Object defaultVal)
{
long newTime = m_file.lastModified();
// 檢查屬性文件是否被其他程序
// (多數情況是程序員手動)修改過
// 假如是,重新讀取此文件

if(newTime == 0)
{
// 屬性文件不存在
if(m_lastModifiedTime == 0)
{
System.err.println(PFILE
+ " file does not exist!");
}
else
{
System.err.println(PFILE
+ " file was deleted!!");
}
return defaultVal;
}
else if(newTime > m_lastModifiedTime)
{
// Get rid of the old properties
m_props.clear();
try
{
m_props.load(new FileInputStream(PFILE));
}
catch(Exception e)
{
e.printStackTrace();
}
}
m_lastModifiedTime = newTime;
Object val = m_props.getProperty(name);
if( val == null )
{
return defaultVal;
}
else
{
return val;
}
}
}
  在上面直接使用了一個局域的常量儲存儲屬性文件的路徑。在實際的系統中,讀者可以采取更靈活的方式將屬性文件的路徑傳入。

  讀者可以看到,這個治理器類有一個很有意思的功能,即在每一次調用時,檢查屬性文件是否已經被更新過。假如確實已經被更新過的話,治理器會自動重新加載屬性文件, 從而保證治理器的內容與屬性文件的內容總是一致的。

  怎樣調用屬性治理器

  下面的源代碼演示了怎樣調用ConfigManager 來讀取屬性文件。

  代碼清單7:怎樣調用ConfigManager 類以讀取屬性文件



發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 乡宁县| 卓尼县| 永康市| 诸暨市| 修武县| 元阳县| 江安县| 桦川县| 泸州市| 井冈山市| 哈巴河县| 天水市| 民丰县| 马公市| 两当县| 自治县| 承德县| 墨脱县| 丰原市| 阿坝县| 华容县| 蕲春县| 北辰区| 长春市| 南充市| 教育| 汶上县| 游戏| 廉江市| 安平县| 樟树市| 阳朔县| 云林县| 清苑县| 舒城县| 青阳县| 瓮安县| 新民市| 通江县| 房山区| 敖汉旗|