将默认字符串参数传递给特性导致的C#编译器错误
本文关键字:编译器 错误 字符串 默认 参数传递 | 更新日期: 2023-09-27 18:07:59
为什么下面的代码会给我一个异常:
CSC错误CS0182:属性参数必须是属性参数类型的常量表达式、typeof表达式或数组创建表达式
在我的构建服务器上?
/// Customer.cs...
[Search(SearchAttribute.SearchDisplay.Regular)]
public Category Category
{
get; set;
}
public enum Category : byte
{
X = 0x01,
Y = 0x02,
...
}
/// SearchAttribute.cs...
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)]
public class SearchAttribute : Attribute
{
public SearchDisplay Display { get; private set; }
public enum SearchDisplay
{
None = (byte) 0x01,
Regular = (byte) 0x02
}
public SearchAttribute(SearchDisplay display, string columnName = null)
: base()
{
Display = display;
}
}
非常感谢。
令人愤怒的是,它在VS2012中构建得很好。我不确定服务器上运行的是什么版本的编译器,但我可以肯定它不是2012年的版本。
更新
多亏了下面的回答者,我明白了:
我正在使用VS2012,但生成服务器仍在使用VS2010生成过程。当在属性中使用空值默认参数时,VS2010/C#4编译器中会出现一个错误。我可以绕过这3种方法:
- 不使用默认参数-
public SearchAttribute(SearchDisplay display, string columnName)
- 使用空字符串-public SearchAttribute(SearchDisplay显示,字符串columnName="(
- 更新我的生成服务器
我现在和2一起去。3是我需要在另一个时间考虑的事情。
我认为Customer.cs
文件在一个单独的程序集(C#项目(中,该程序集引用SearchAttribute.cs
所在的程序集。
为了使枚举SearchDisplay
和构造函数中的可选参数columnName
正常工作,必须按照正确的顺序重新编译这两个程序集。我怀疑您的构建服务器上并非如此。依赖程序集可能是通过引用SearchAttribute
所在程序集的旧版本编译的。
更新
查看右侧的所有链接线程。他们说这是一个用Visual Studio 2012(C#5编译器(修复的错误。只有当可选参数的默认值为null
时才会发生这种情况。在我的第一个测试中,我做出了一个愚蠢的决定,使用另一个字符串(这是可以识别的(,但这不会发生在另一个串中。(将删除我在下面的评论。(
当属性的用法与属性类本身在同一程序集中时,为null
文本提供显式类型会有所帮助,如:
public SearchAttribute(SearchDisplay display, string columnName = (string)null)
...
有了这一点,只要所有的用法都与上面的构造符在同一个集合中,它似乎就起作用了。但是,在您的情况下,它们位于不同的程序集中。
如果你愿意使用空字符串,问题就会消失:
public SearchAttribute(SearchDisplay display, string columnName = "")
...
否则,我建议你使用旧的前C#-4风格
[Search(SearchAttribute.SearchDisplay.Regular)]
public Category Category
...
[Search(SearchAttribute.SearchDisplay.Regular, ColumnName = "Changed!")]
public Category AnotherCategory
...
只要有一个名为ColumnName
的类成员(实例属性或字段(,就可以在构造函数中不使用columnName
参数。该ColumnName
不得为只读或仅获取。
你不是说吗
[Search(SearchAttribute.SearchDisplay.Regular)]