为什么“十进制”不是一个有效的属性参数类型?

这是真的难以置信,但真实的。这个代码将不工作:

[AttributeUsage(AttributeTargets.Property|AttributeTargets.Field)]
public class Range : Attribute
{
public decimal Max { get; set; }
public decimal Min { get; set; }
}


public class Item
{
[Range(Min=0m,Max=1000m)]  //compile error:'Min' is not a valid named attribute argument because it is not a valid attribute parameter type
public decimal Total { get; set; }
}

当这个起作用的时候:

[AttributeUsage(AttributeTargets.Property|AttributeTargets.Field)]
public class Range : Attribute
{
public double Max { get; set; }
public double Min { get; set; }
}


public class Item
{
[Range(Min=0d,Max=1000d)]
public decimal Total { get; set; }
}

谁能告诉我为什么双精度是可以的,而小数是不可以的。

50676 次浏览

来自 规格:

属性类的位置参数和命名参数的类型 仅限于属性参数类型,即:

  • 以下类型之一: boolbytechardoublefloatintlongsbyteshortstringbyte0、 byte1、 byte2。
  • object型。
  • System.Type型。
  • 枚举类型,前提是它具有公共可访问性,并且它所嵌套的类型(如果有的话)也具有公共可访问性(属性规范)。
  • 上述类型的单维数组。

这是 CLR 限制 基元常数或基元数组 基元可以用作属性 原因是 属性必须完全编码在 元数据。这不同于 在 IL 中编码的方法体。 使用 MetaData 只会严格限制 可以使用的值的范围。 在 CLR 的当前版本中, 元数据值仅限于 类型和数组 原语(可能遗漏了一个未成年人) 一)。

摘自 这个答案由 JaredPar

Decimals 虽然一个基本类型不是一个 基元类型,因此不能是 以元数据表示,以防止 它是一个属性参数。

这个问题的答案是使用字符串,尽管字符串不是原子类型,但允许将其作为属性。不要使用双精度,因为四舍五入会降低结果的准确性。

public String MinimumValue
{
get
{
return minimumValueDecimal.ToString();
}


set
{
minimumValueDecimal = Decimal.Parse(value);
}
}


private decimal minimumValueDecimal;