У меня есть следующий интерфейс VB.net, который мне нужно перенести на C#. C# не допускает перечисления в интерфейсах. Как я могу перенести это без изменения кода, который использует этот интерфейс?
Public Interface MyInterface
Enum MyEnum
Yes = 0
No = 1
Maybe = 2
End Enum
ReadOnly Property Number() As MyEnum
End Interface





public enum MyEnum
{
Yes = 0,
No = 1,
Maybe = 2
}
public interface IMyInterface
{
MyEnum Number { get; }
}
Короче говоря, вы не можете изменить этот интерфейс, не нарушив код, потому что C# не может вкладывать типы в интерфейсы. Когда вы реализуете интерфейс версий VB.NET, вы указываете, что Number будет возвращать тип MyInterface.MyEnum:
class TestClass3 : TestInterfaces.MyInterface
{
TestInterfaces.MyInterface.MyEnum TestInterfaces.MyInterface.Number
{
get { throw new Exception("The method or operation is not implemented."); }
}
}
Однако, поскольку C# не может вкладывать типы внутри интерфейсов, если вы отключите перечислитель от интерфейса, вы вернете другой тип данных: в данном случае MyEnum.
class TestClass2 : IMyInterface
{
MyEnum IMyInterface.Number
{
get { throw new Exception("The method or operation is not implemented."); }
}
}
Подумайте об этом, используя полное имя типа. В интерфейсе VB.NET у вас есть возвращаемый тип
MyProject.MyInterface.MyEnum
В интерфейсе C# у вас есть:
MyProject.MyEnum.
К сожалению, код, реализующий интерфейс VB.NET, должен быть изменен для поддержки того факта, что тип, возвращаемый MyInterface.Number, изменился.
IL поддерживает типы вложенности внутри интерфейсов, поэтому остается загадкой, почему C# этого не делает:
.class public interface abstract auto ansi MyInterface
{ .property instance valuetype TestInterfaces.MyInterface / MyEnum Number { .get instance valuetype TestInterfaces.MyInterface / MyEnum TestInterfaces.MyInterface :: get_Number () }
.class auto ansi sealed nested public MyEnum
extends [mscorlib]System.Enum
{ .field общедоступный статический литерал типа TestInterfaces.MyInterface / MyEnum Maybe = int32 (2)
.field public static literal valuetype TestInterfaces.MyInterface/MyEnum No = int32(1)
.field public specialname rtspecialname int32 value__
.field public static literal valuetype TestInterfaces.MyInterface/MyEnum Yes = int32(0)
}
}
Если у вас много кода в других сборках, использующих этот интерфейс, лучше всего хранить его внутри отдельной сборки VB.NET и ссылаться на него из своих проектов C#. В противном случае его можно преобразовать, но вам придется изменить любой код, который его использует, чтобы вернуть другой тип.
Это нарушает код, использующий интерфейс. Я бы хотел этого избежать, если возможно.