一个简单的配置管理器(SettingManager)
在很多.net开发的项目中,我们几乎都会使用到一些自定义的参数,比如说第三方的配置参数之类的.
他们的特点是:1.系统全局 2,可以做成键值对(Dictionary).
我们可以将这些参数放到Web.config,xml或者数据库表中,当然部分不常变的可以直接写在程序中.
为了方便我通常喜欢将他们统放在一个配置管理器中,然后希望别人使用时, 可以像使用AppSetings中的参数一样

初看起来还是比较容易实现,在ConfiguratonManager中定义一个公开属性AppSettings就好了.
实现如下:
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks; namespace ConfigManager
{
public class ConfigurationContainer
{
private static ConfigurationContainer m_Instance = null; public static ConfigurationContainer Instance
{
get
{
if (m_Instance == null)
m_Instance = new ConfigurationContainer();
return m_Instance;
}
} private ConfigurationContainer()
{ } private ReadOnlyDictionary<string, string> _configuration;
private Dictionary<string, string> _mutableConfiguration; public ReadOnlyDictionary<string, string> Configuration
{
get
{
//TODO:check is newest or not in database??
if (_mutableConfiguration == null)
Init(); _configuration =
new ReadOnlyDictionary<string, string>(_mutableConfiguration);
return _configuration;
}
} public bool Add(string key, string value)
{
bool bRet = false;
if (!_mutableConfiguration.ContainsKey(key))
{
_mutableConfiguration.Add(key, value);
bRet = true;
}
return bRet;
} public bool Update(string key, string value)
{
bool bRet = false;
if (_mutableConfiguration.ContainsKey(key))
{
_mutableConfiguration[key] = value;
bRet = true;
}
return bRet;
} public bool Remove(string key)
{
bool bRet = false;
if (_mutableConfiguration.ContainsKey(key))
{
_mutableConfiguration.Remove(key);
bRet = true;
}
return bRet;
} //private bool ConfigurationAllowed(string key, string value)
//{
// // Put in your checks and balances
// // here and return the appropriate result
// return true;
//} private void Init()
{
_mutableConfiguration = new Dictionary<string, string>();
_mutableConfiguration.Add("key", "value");
_mutableConfiguration.Add("key1", "value1");
_mutableConfiguration["key2"] = "value2";
}
}
}
ConfigurationContainer: using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks; namespace ConfigManager
{
public class ConfigManager
{
private static IReadOnlyDictionary<string, string> _AppSettings = null;
public static IReadOnlyDictionary<string, string> Appettings
{
get
{
//initial ensurer the newest
_AppSettings = ConfigurationContainer.Instance.Configuration;
return _AppSettings;
}
} //Exception:Violence to Add
public static void BeNaughtyWithConfiguration()
{
IDictionary<string, string> convertToReadWrite
= (IDictionary<string, string>)_AppSettings;
//ConfigElement element = convertToReadWrite["key"];
//element.Value = "Haa Haa";
//Console.WriteLine(element.Value);
//Console.WriteLine(convertToReadWrite["key"]);
//Console.ReadLine(); convertToReadWrite.Add("Key12345", "xsds");
} public static bool Add(string key, string value)
{
return ConfigurationContainer.Instance.Add(key, value);
} public static bool Update(string key, string value)
{
return ConfigurationContainer.Instance.Update(key, value);
} public static bool Remove(string key)
{
return ConfigurationContainer.Instance.Remove(key);
}
}
}
最底层是一个单例模式,并封装了字典的CRUD操作。
客户端测试一下:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks; namespace ConfigManager
{
class Program
{
static void Main(string[] args)
{
var settings = ConfigManager.Appettings; foreach(var item in settings)
{
Console.WriteLine("key:{0},value:{1}",item.Key,item.Value);
} var t1 = ConfigManager.Appettings["key1"]; //test add
ConfigManager.Add("t","test");
//var t2 = ConfigManager.Appettings;
//update
ConfigManager.Update("t","test123"); //remove
ConfigManager.Remove("t"); Console.ReadKey();
}
}
}

好像也能运行。
那么,问题来了!测试代码改一改,
//test not item in Dictionary
var t2 = ConfigManager.Appettings["luckyhu"];

代码崩溃了,老兄!
其实上面的代码能够满足一般的需求,但是对使用着来说,仍然不太方便.所以我和同事进一步优化了上述代码.
现在变得更加简洁了.
public class SettingManager : Dictionary<string, string>
{
private static SettingManager _Settings = null;
public static SettingManager Settings
{
get
{
if (_Settings == null)
_Settings = new SettingManager();
return _Settings;
}
} private SettingManager()
{
//Init Data
//DataSoure:truely data here...
for (int i = ; i < ; i++)
{
var key = String.Format("key{0}", i);
var value = String.Format("value{0}", i);
if (!this.Keys.Contains(key))
this.Add(key, value);
}
} public string this[string key]
{
get
{
if (!this.ContainsKey(key))
return String.Empty;
return base[key];
}
set
{
base[key] = value;
}
} public static bool GetBoolValue(string key)
{
bool value = false;
bool.TryParse(Settings[key], out value);
return value;
} public static int GetIntValue(string key)
{
int value = ;
int.TryParse(Settings[key], out value);
return value;
}
}
大家看到代码简洁了不少,有了以下改进:
1.代码变少了
2.可以控制索引的返回结果了
3.更多的利用了Dictionary自身的特性,如CRUD
4.增加了自定义类型转换方法
总之,这些努力都是为了方便别人使用.
好吧,看看客户端测试吧

测试结果是OK的
好了,这样一个通用的配置管理器完成了, 当然有更多的需求,还可以对其进行扩展。欢迎大家不吝赐教 .
祝大家新年快乐,万事如意! 2015,一起任性!

一个简单的配置管理器(SettingManager)的更多相关文章
- python使用tcp实现一个简单的下载器
上一篇中介绍了tcp的流程,本篇通过写一个简单的文件下载器程序来巩固之前学的知识. 文件下载器的流程如下: 客户端: 输入目标服务器的ip和port 输入要下载文件的名称 从服务器下载文件保存到本地 ...
- 自己写的一个简单PHP采集器
自己写的一个简单PHP采集器 <?php //**************************************************************** $url = &q ...
- [SimplePlayer] 实现一个简单的播放器
简单的播放器需要实现一个最基本的功能:播放视频文件. 实现这个功能需要包含以下几个步骤: 从视频文件中提取视频图像 在屏幕上显示视频图像 视频帧的同步,也就是保证视频图像在合适的时间在屏幕上显示 从视 ...
- C++写一个简单的解析器(分析C语言)
该方案实现了一个分析C语言的词法分析+解析. 注意: 1.简单语法,部分秕.它可以在本文法的基础上进行扩展,此过程使用自上而下LL(1)语法. 2.自己主动能达到求First 集和 Follow 集. ...
- 第二十四篇-用VideoView制作一个简单的视频播放器
使用VideoView播放视频,视频路径有三种: 1. SD卡中 2. Android的资源文件中 3. 网络视频 第一种,SD卡中的方法. 路径写绝对路径,如果不能播放,可以赋予读取权限. 效果图: ...
- Android开发6:Service的使用(简单音乐播放器的实现)
前言 啦啦啦~各位好久不见啦~博主最近比较忙,而且最近一次实验也是刚刚结束~ 好了不废话了,直接进入我们这次的内容~ 在这篇博文里我们将学习Service(服务)的相关知识,学会使用 Service ...
- iOS之基于FreeStreamer的简单音乐播放器(模仿QQ音乐)
代码地址如下:http://www.demodashi.com/demo/11944.html 天道酬勤 前言 作为一名iOS开发者,每当使用APP的时候,总难免会情不自禁的去想想,这个怎么做的?该怎 ...
- AVPlayer的使用+简单的播放器Demo
学习内容 AVPlayer学习 几个播放器相关的类 AVPlayer.AVURLAsset.AVPlayerItem.AVPlayerLayer //控制播放器的播放.暂停.播放速度 @propert ...
- 【模块化编程】理解requireJS-实现一个简单的模块加载器
在前文中我们不止一次强调过模块化编程的重要性,以及其可以解决的问题: ① 解决单文件变量命名冲突问题 ② 解决前端多人协作问题 ③ 解决文件依赖问题 ④ 按需加载(这个说法其实很假了) ⑤ ..... ...
随机推荐
- webbench之使用(二)
[root@lam7 ~]# webbench -helpwebbench [option]... URL -f|--force Don't wait for reply ...
- OneThink开发框架
OneThink是一个开源的内容管理框架,基于最新的ThinkPHP3.2版本开发,提供更方便.更安全的WEB应用开发体验,采用了全新的架构设计和命名空间机制,融合了模块化.驱动化和插件化的设计理念于 ...
- SpringMVC 常用注解(1)
/** * @RequestMapping 除了修饰方法 还可以修饰类 * 1).类定义处:提供初步的请求映射信息,相当于WEB应用的根目录 * 2).方法定义处,提供进一步的细分映射信息,相对 ...
- React使用jquery方式动态获取数据
好久没写react了,今天有空写一下来react实现实时请求数据,并刷新数据的小demo. 首先我还是选择了jquery方式中自带的ajax获取数据,首先要引用所需的js包 接下来要写一个自定义的js ...
- JS省市区三级联动
不需要访问后台服务器端,不使用Ajax,无刷新,纯JS实现的省市区三级联动. 当省市区数据变动是只需调正js即可. 使用方法: <!DOCTYPE html><html>< ...
- 在DrawingVisual上绘制圆形的进度条,类似于IOS系统风格。
1.说明:在WPF中,文件下载时需要显示下载进度,由于系统自带的条型进度条比较占用空间,改用圆形的进度条,需要在DrawingVisual上呈现. 运行的效果如图: private Point Get ...
- Leetcode Candy
There are N children standing in a line. Each child is assigned a rating value. You are giving candi ...
- Easyui的Dialog的toolbar的自定义添加
最近一直在写快速定制Web表格,基于Easyui,整个过程使用了大量的Easyui的dialog,每个dialog的代码大部分都雷同,感觉代码出现了很大程度的重复,然后想写一个通用的dialog设置函 ...
- BZOJ4572: [Scoi2016]围棋
Description 近日,谷歌研发的围棋AI—AlphaGo以4:1的比分战胜了曾经的世界冠军李世石,这是人工智能领域的又一里程碑. 与传统的搜索式AI不同,AlphaGo使用了最近十分流行的卷积 ...
- Eclipse中的文件导航插件StartExplorer
在Eclipse里面,想找到文件的位置是件麻烦的事,需要借助插件,我用的是StartExplorer插件. StartExplorer官方地址:http://startexplorer.sourcef ...