在这里进行了广泛的搜索后,我仍然需要一个专家建议:
要求
要求非常标准:将int常量映射到资源文件中的字符串,这样本地化就可以很好地工作,我们可以很容易地用当前用户语言为下拉列表创建一个值对列表,并对int值进行反向查找。Const整数在不同的类中被定义为静态。
因此,以下是它目前的实施方式,告诉我它可以更好,值得批评:
字典类:
public class TLiteralDic : Dictionary<int, string>
{
//Lookup method
public string getLiteral(int key)
{
if (ContainsKey(key)) {
return this[key];
}
return string.Empty;
}
}
在靠近UI层的某个地方,一个填充下拉控件的扩展方法定义如下:
public static void fill(this TLiteralDic dic, DropDownList ddlst)
{
ddlst.Items.Clear();
foreach (KeyValuePair<int, string> v in dic) {
ddlst.Items.Add(new ListItem(v.Value, v.Key.ToString()));
}
}
正在添加对(静态常量int到资源文件中的字符串):
public static class TLiterals
{
private static TLiteralDic _fileStatus;
public static TLiteralDic FileStatus
{
get
{
if (_fileStatus == null) {
_fileStatus = new TLiteralDic() {
{TFiles.Status.Cancelled, Lists.FileStatus_Cancelled},
{TFiles.Status.Closed, Lists.FileStatus_Closed},
{TFiles.Status.OnHold, Lists.FileStatus_OnHold},
{TFiles.Status.Open, Lists.FileStatus_Open},
{TFiles.Status.Pending, Lists.FileStatus_Pending},
{TFiles.Status.Portal, Lists.FileStatus_Portal}
};
}
return _fileStatus;
}
}
//... hundred of lists like that, short and long (up to 15 entries)
}
在代码中使用
查找:
textStatus.Text = TLiterals.FileStatus.getLiteral(row.FileStatus);
列表填写:
TLiterals.FileStatus.fill(ddlstFileStatus);
注意事项
这个想法是只有一个定义映射的地方,并且能够从中创建一个列表或按int值进行查找。理想情况下具有良好的性能、最小的内存占用和编码麻烦。
已经考虑了以下备选方案:
- 使用开关(过去用于查找-大量冗余代码)
- 使用反射
- 闭包
- JSON,XML
- 在VS2010中使用T4类生成
到目前为止,还没有找到简单或明显更好的解决方案。
当前实施中的问题
- 在实际的对列表中有很多重复的代码,理想情况下必须全部隐藏并重用
- 需要定义静态私有财产;其想法是,只有在第一次检索列表时,才对列表使用"惰性"初始化
- 在第一次使用后将文字保留在内存中对于这种简单的操作来说可能代价太高
当前实施的优势
在一个地方定义的- 列表(与使用相同值对在两个不同地方进行切换查找和手动列表填充相比)
- 用于查找和列表填充的重用代码
- 易于维护和编译时间检查
有什么更好的"漂亮代码"的想法吗?:)
理想情况下,我希望在定义列表时看到这样的东西,但在真正需要/使用之前,它不应该初始化:
public static TLiteralDic FileStatus = new TLiteralDic () {
{TFiles.Status.Cancelled, Lists.FileStatus_Cancelled},
{TFiles.Status.Closed, Lists.FileStatus_Closed},
{TFiles.Status.OnHold, Lists.FileStatus_OnHold},
{TFiles.Status.Open, Lists.FileStatus_Open},
{TFiles.Status.Pending, Lists.FileStatus_Pending},
{TFiles.Status.Portal, Lists.FileStatus_Portal}
}
在真正需要/使用之前不应该初始化:
您可以使用惰性实例化来完成此操作:
Lazy<Dictionary<string, string>> resources = new Lazy<Dictionary<string, string>>(() => new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase));
对字典进行排序也有助于加快搜索速度,例如使用BinarySearch。