如何在不指定命名空间的情况下消除字段的枚举歧义
本文关键字:情况下 字段 歧义 枚举 命名空间 | 更新日期: 2023-09-27 18:08:46
enum SameName { Value }
class Tester
{
void Method1() {
SameName SameName;
SameName test = SameName.Value;
}
void Method2() {
string SameName;
SameName test = SameName.Value;
}
}
在第一种方法中,编译器正确地推断出 SameName.Value 引用枚举。
在第二种方法中,编译器感到困惑,并认为 SameName.Value 引用的是字符串类的 Value 成员。由于不存在这样的成员,因此会出错。
在这种情况下,我可以做些什么来帮助编译器更了解我的 SameName 枚举?有没有办法使用语句来做到这一点?
- 我无法在我的真实代码中重命名变量或枚举。 我
- 正在创建一个包含许多枚举值的大型字典,我宁愿不在枚举的每个实例前面添加命名空间前缀。
更新:是的,我知道我不应该使用大写的局部变量。是的,我意识到这些是局部变量,而不是字段。是的,我意识到如果真正的代码看起来像这样,调试起来会很糟糕。我把上面写成一个简短的、人为的例子,展示了我在实际代码中遇到的问题。我很抱歉我没有明确表达我的意图。在实际代码中,类位于枚举命名空间中包含的命名空间中,局部变量是基类中的属性。我试图删除所有无关的代码以使问题更容易发现,并列出了我的要求,以便为问题提供一点范围。
好的,根据您的更新,我认为我们可以为您提供帮助。现在的情况更有意义了。我想有代码:
// in a place you're not allowed to edit
namespace Outer
{
public enum SameName { Value, }
}
和
// in a place you're not allowed to edit
namespace BaseSpace
{
public class TesterBase
{
public string SameName { get; set; }
}
}
然后您在可以编辑的第三个代码文件中遇到了问题。我建议你用指向类型的using
别名指令来解决它。这样,您就不必一遍又一遍地重复完整的命名空间。它将看起来像这样:
using BaseSpace;
using snEnum = Outer.SameName; // this helps you (a using alias)
namespace Outer.Inner
{
public class Tester : TesterBase
{
void Method2() {
snEnum test = snEnum.Value;
}
}
}
请注意,使用 alias 指令可以"指向"命名空间或类型(如本例所示(。他们为您提供了一个您经常使用的繁琐名称的简写。
您可以为枚举类型使用别名:
namespace ConsoleApplication13
{
using NewEnumName = ConsoleApplication13.SameName;
internal enum SameName { Value }
internal class Tester
{
private void Method1()
{
SameName SameName;
SameName test = SameName.Value;
}
private void Method2()
{
string SameName;
SameName test = NewEnumName.Value;
}
}
public class Program
{
private static void Main(string[] args)
{
Console.ReadKey();
}
}
}
C# 被设计为在面对与其类型相同的属性时变得健壮,因为这很常见:
class Shape
{
public Color Color { get; set; }
...
如果你有一个颜色类型,那么有一个也称为 Color 的属性是很常见的,并且没有很好的方法来重命名它们中的任何一个。 因此,C# 旨在合理优雅地处理这种情况。 请参阅我 2009 年的文章,了解有关颜色问题的一些有趣细节:
http://blogs.msdn.com/b/ericlippert/archive/2009/07/06/color-color.aspx
C# 不是为在声明的事物是本地事物时处理颜色颜色问题而设计的。重命名本地。
这样的原因,最好使用约定来命名局部变量sameName
。 下面是一个完整的示例:
enum SameName { Value }
class Tester
{
void Method1() {
SameName sameName;
SameName test = SameName.Value;
}
void Method2() {
string sameName;
SameName test = SameName.Value;
}
}
您说无法重命名字段,但您的示例显示了局部变量。 按照惯例,字段只能是私有的,不要以大写字母开头。 局部变量和私有字段可以,但极少数例外(例如反射...如果你正在反映私有领域,你还有其他问题(,总是重命名以适应你需要的任何内容。
简而言之,使用良好做法,您就不会遇到此问题。
这不是一个真正的答案。而是受以下问题启发的观察:
测验:这段代码输出什么(假设System.Object
有实例方法ToString()
和GetHashCode()
(?
class Color
{
private static new int ToString()
{ return 42; }
public static new string GetHashCode()
{ return "I'm public!"; }
}
static class Program
{
static void Main()
{
Color Color = new Color();
var testA = Color.ToString();
var testB = Color.GetHashCode();
Console.WriteLine(testA);
Console.WriteLine(testB);
}
}
答:由于Color
定义了与其继承的实例方法具有相同名称和签名的新静态方法,因此编译器可以选择两个重载。在ToString
的情况下,它选择实例方法,这很幸运,因为静态方法是私有的。但是对于GetHashCode
,它选择了静态方法。颜色-颜色魔法。
补充说明:对于那些反对用大写首字母命名局部变量的人,当 Color-Color 是直接类成员时,可以做同样的例子,例如 public static Color Color { get; set; }
.