java进阶(三) 用单例模式加载配置文件

来源:互联网 发布:淘宝注册资金 编辑:程序博客网 时间:2024/06/08 11:11

在实际开发中,经常需要加载配置文件,在读取配置文件的过程中,我们只需要初始化一次即可。就想到了用单例模式来加载配置文件,最常用的单例模式有四种:懒汉式(线程安全,延迟加载,线程阻塞),饿汉式(线程安全,不会延迟加载,响应迅速),匿名内部类(线程安全,延迟加载,响应迅速),枚举。


综合考虑,使用匿名内部类的方式加载配置文件(根据自己的业务场景,挑选)比较好。

当时用getXXXByKey()方法后,会自动扫描和XXX.properties同级目录下的所有properties文件,文件编码以调用此方法的编码为准(默认UTF-8),例如:调用getStringByKey("mysql.properties", "mysql.url","UTF-8"),在第一次调用时会自动扫描和mysql.properties同级目录下的所有properties文件,使用UTF-8编码解析文件,然后返回mysql.properties文件中mysql.url所对应的value值。

以下是实现方式:

public class PropertiesUtil {/** * 私有化构造函数,防止类被实例化 * @date 2017年3月9日 */private PropertiesUtil(String filePath, String encode) {File file = new File(filePath);File[] array = file.listFiles();for(File childfile : array) {String childFileName = childfile.getName();if(!childFileName.endsWith("properties")) continue;loadConfigProperties(childFileName, encode);}}/** * 存放配置文件的所有的key-value * 以这种方式存储是为了防止多个配置文件间存在key冲突 */private Map<String, HashMap<String,String>> allParam = new HashMap<String, HashMap<String, String>>();/** * 默认的properties文件名 */private static final String DEFAULT_PROPERTIES_NAME = "config.properties";/** * 解析properties文件默认编码 */private static final String DEFAULT_ENCODE = "UTF-8";/** * 解析properties文件编码 */private static String fileEncode = null;  /** * properties文件所在的地址 */private static String propertiesParentPath = null;        /** * 根据文件名称-key,返回相应key的值 * 文件名默认为config.properties,文件编码默认为UTF-8 * @date 2016年11月7日 */    public static Integer getIntegerByKey(String key) {    return Integer.parseInt(getStringByKey(DEFAULT_PROPERTIES_NAME, key, DEFAULT_ENCODE));    }        /**     * 根据文件名称-key,返回相应key的值,文件编码默认为UTF-8     * @param fileName 文件名     * @param key properties文件中key的名称     * @date 2017年3月9日     */    public static Integer getIntegerByKey(String fileName, String key) {    return Integer.parseInt(getStringByKey(fileName, key, DEFAULT_ENCODE));    }        /**     * 根据文件名称-key,返回相应key的值     * @param fileName 文件名     * @param key properties文件中key的名称     * @param encode 文件编码     * @date 2017年3月9日     */    public static Integer getIntegerByKey(String fileName, String key, String encode) {    return Integer.parseInt(getStringByKey(fileName, key, encode));    }        /** * 根据文件名称-key,返回相应key的值 * 文件名默认为config.properties,文件编码默认为UTF-8 * @date 2016年11月7日 */    public static Boolean getBooleanByKey(String key) {    return Boolean.parseBoolean(getStringByKey(DEFAULT_PROPERTIES_NAME, key, DEFAULT_ENCODE));    }        /**     * 根据文件名称-key,返回相应key的值,文件编码默认为UTF-8     * @param fileName 文件名     * @param key properties文件中key的名称     * @date 2017年3月9日     */    public static Boolean getBooleanByKey(String fileName, String key) {    return Boolean.parseBoolean(getStringByKey(fileName, key, DEFAULT_ENCODE));    }        /**     * 根据文件名称-key,返回相应key的值     * @param fileName 文件名     * @param key properties文件中key的名称     * @param encode 文件编码     * @date 2017年3月9日     */    public static Boolean getBooleanByKey(String fileName, String key, String encode) {    return Boolean.parseBoolean(getStringByKey(fileName, key, encode));    }        /** * 根据文件名称-key,返回相应key的值 * 文件名默认为config.properties,文件编码默认为UTF-8 * @date 2016年11月7日 */    public static Long getLongByKey(String key) {    return Long.parseLong(getStringByKey(DEFAULT_PROPERTIES_NAME, key, DEFAULT_ENCODE));    }        /**     * 根据文件名称-key,返回相应key的值,文件编码默认为UTF-8     * @param fileName 文件名     * @param key properties文件中key的名称     * @date 2017年3月9日     */    public static Long getLongByKey(String fileName, String key) {    return Long.parseLong(getStringByKey(fileName, key, DEFAULT_ENCODE));    }        /**     * 根据文件名称-key,返回相应key的值     * @param fileName 文件名     * @param key properties文件中key的名称     * @param encode 文件编码     * @date 2017年3月9日     */    public static Long getLongByKey(String fileName, String key, String encode) {    return Long.parseLong(getStringByKey(fileName, key, encode));    }        /** * 根据文件名称-key,返回相应key的值 * 文件名默认为config.properties,文件编码默认为UTF-8 * @date 2016年11月7日 */    public static String getStringByKey(String key){return getStringByKey(DEFAULT_PROPERTIES_NAME, key, DEFAULT_ENCODE);    }        /**     * 根据文件名,key返回value值,文件编码默认为UTF-8     * @date 2016年11月7日     */    public static String getStringByKey(String fileName, String key) {    return getStringByKey(fileName, key, DEFAULT_ENCODE);    }    /** * 根据文件名,key,编码返回value值 * @date 2016年11月7日 */public static String getStringByKey(String fileName, String key, String encode) {String propertiesPath = PropertiesUtil.class.getClassLoader().getResource(fileName).getPath().replace(fileName, "");propertiesParentPath = propertiesPath;fileEncode = encode;return PropertiesUtilHolder.instance.allParam.get(fileName).get(key);} /** * 静态内部类,单例模式,保证只有一个实例变量 * @date 2017年5月16日 */private static class PropertiesUtilHolder {private static PropertiesUtil instance = new PropertiesUtil(propertiesParentPath, fileEncode);}/** * 加载配置文件,需要进行加锁 * @date 2017年5月3日 */private void loadConfigProperties(String fileName, String encode) {InputStream in = null;try {Properties p = new Properties();File file = new File(fileName);if(file.exists()) {p.load(new FileInputStream(file));} else {in = PropertiesUtil.class.getClassLoader().getResourceAsStream(fileName);// 解决中文乱码BufferedReader bf = new BufferedReader(new InputStreamReader(in, encode));p.load(bf);}Set<Entry<Object, Object>> allKey = p.entrySet();HashMap<String, String> paramMap = new HashMap<String, String>();for (Entry<Object, Object> entry : allKey) {paramMap.put(String.valueOf(entry.getKey()), String.valueOf(entry.getValue()));}allParam.put(fileName, paramMap);} catch (IOException e) {e.printStackTrace();} finally {try {if(in != null) in.close();} catch (IOException e) {e.printStackTrace();}}}}