Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/334.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 枚举的自定义属性是否危险?_C#_Attributes_Enums - Fatal编程技术网

C# 枚举的自定义属性是否危险?

C# 枚举的自定义属性是否危险?,c#,attributes,enums,C#,Attributes,Enums,我正在构建一个大量使用Enums定制数据的应用程序。基本上,一个对象存储在数据库中,具有大约28个单独的属性。每个属性都是一个两个字符的字段,从SQL直接转换为Enum 不幸的是,我还需要将这些值转换为两个不同的人类可读值。一个用于数据表上的图例,另一个用于CSS类在web应用程序前端设置图像样式 为此,我设置了两个自定义属性,并在必要时将它们应用于Enum。例如: 自定义属性接口 public interface IAttribute<T> { T Value { get;

我正在构建一个大量使用
Enum
s定制数据的应用程序。基本上,一个对象存储在数据库中,具有大约28个单独的属性。每个属性都是一个两个字符的字段,从SQL直接转换为
Enum

不幸的是,我还需要将这些值转换为两个不同的人类可读值。一个用于数据表上的图例,另一个用于CSS类在web应用程序前端设置图像样式

为此,我设置了两个自定义属性,并在必要时将它们应用于
Enum
。例如:

自定义属性接口

public interface IAttribute<T>
{
    T Value { get; }
}
public sealed class AbbreviationAttribute: Attribute, IAttribute<string>
{
    private readonly string value;

    public AbbreviationAttribute(string value)
    {
        this.value = value;
    }

    public string Value
    {
        get { return this.value; }
    }
}
示例
Enum
使用此模式

缩写
说明
都是实现
IAttribute
的自定义属性。我的实际
Enum
有11个可能的值,正如我前面提到的,它在我的自定义对象的28个单独属性中使用。使用自定义属性似乎是来回映射此信息的最佳方式

现在的问题是,这是实现这一目标的最佳方式吗?我将
Enum
值(“上面代码段中的C”、“NF”或“CP”)存储在数据库中,但我需要代码中缩写和描述的值。此外,我怀疑这将是我需要的最后一组自定义属性


在我继续推进这一模式之前。。。这是正确的做事方式吗?我宁愿现在就用这种方法修复潜在的问题,也不愿以后再进行跟踪和重构。

您能更改数据库吗?我认为最好的选择是制作一个表(或多个表)来容纳枚举的可能值,并将主要对象的外键传递给它(而不是使用字符代码-这使它更容易拉入并规范化您的数据库)。为表指定一个
缩写
说明
列,然后将它们拉入并按键引用,如果查找速度慢,则缓存它们


属性的一个危险之处是,如果这些字符串中的任何一个必须更改,那么这就是应用程序的完全重新部署。如果将它们设置为数据库值,则可以通过简单的
更新

来更改它们。这与我使用的方法相同。一个缺点是序列化。自定义属性值不会序列化


与数据库方法相比,我更喜欢自定义属性方法,因为它将属性数据正确地绑定到枚举,而不必使用查找表或类等。

我可能会为类似的内容构建一个哈希表和一个特殊类型。您可能已经出于某种原因放弃了这个想法,但我不知道您的应用程序的细节

class SpecialType {
  // include the fields and all attributes that you need to reference, ToString method for debugging, and any serialization you need
  public string foo { get; set; }
  public string bar { get; set; }
  public ToString() { return "SpecialType with foo '" + foo + "' and bar '" + bar + "'"; }
}

Dictionary<int, SpecialType> myDict = new Dictionary<int, SpecialType> {
   { 1, new SpecialType { foo = "XA1B2", bar = "XC3D4" } },
   { 2, new SpecialType { foo = "ZA1B2", bar = "ZC3D4" } },
   { 3, new SpecialType { foo = "YA1B2", bar = "YC3D4" } },
}
类特殊类型{
//包括需要引用的字段和所有属性、用于调试的ToString方法以及所需的任何序列化
公共字符串foo{get;set;}
公共字符串条{get;set;}
public-ToString(){return“SpecialType with-foo'”+foo+“'和bar'+bar+”;}
}
字典myDict=新字典{
{1,新的特殊类型{foo=“XA1B2”,bar=“XC3D4”},
{2,新的特殊类型{foo=“ZA1B2”,bar=“ZC3D4”},
{3,新的特殊类型{foo=“YA1B2”,bar=“YC3D4”},
}

然后我可以很容易地在我的其他类中保存int以节省内存,通过检查字典的键中是否存在某个特定的值来确定该值是否有效,等等。如果您最终也打算使用WPF或读/写磁盘,那么进行数据绑定可能会容易得多。

我可以看到一些本地化问题,因为这是一个好问题。不过,我可能会修改
IAttribute
,以支持
gettext
风格的本地化设置。我更关心的是可伸缩性、性能和我可能不知道的最佳实践。
GetAttributeValue
不是一种与前面描述文本相反的扩展方法。我倾向于将枚举提升为一个类,并将11个可能的值放入带有“缩写”和“描述”的表中@JesseC.Slicer是我的错。它最初是一个扩展方法:-)另一个缺点是,如果某个描述发生了很大的变化,您必须完全重新部署应用程序character@eouw0o83hf:是的。最近的部署选项(又称ClickOnce)缓解了这一问题,但您是正确的。我的大多数应用程序往往是web应用程序,或者是部署周期间隔较长的应用程序,在这些应用程序中,许多其他东西都会发生变化,因此更新一些描述并不是什么大问题。
public enum Download
{
    [Abbreviation("check")]
    [Description("Certified")]
    C = 1,

    [Abbreviation("no-formal")]
    [Description("No formal certification")]
    NF = 2,

    [Abbreviation("cert-prob")]
    [Description("Certified with potential problems")]
    CP = 3
}
class SpecialType {
  // include the fields and all attributes that you need to reference, ToString method for debugging, and any serialization you need
  public string foo { get; set; }
  public string bar { get; set; }
  public ToString() { return "SpecialType with foo '" + foo + "' and bar '" + bar + "'"; }
}

Dictionary<int, SpecialType> myDict = new Dictionary<int, SpecialType> {
   { 1, new SpecialType { foo = "XA1B2", bar = "XC3D4" } },
   { 2, new SpecialType { foo = "ZA1B2", bar = "ZC3D4" } },
   { 3, new SpecialType { foo = "YA1B2", bar = "YC3D4" } },
}