将类强制转换为实现接口
本文关键字:实现 接口 转换 | 更新日期: 2023-09-27 17:56:33
我有一个实现两个接口的类:
public class MyService : IServiceA, IServiceB
接口IServiceA
与IServiceB
完全相同,但是当MyService
被实例化为这些接口中的每一个时,一组充当MyService
参数的不同值被加载到内存中:
public static string ServiceIdentifier;
IServiceA myService = new MyService(); // ServiceIdentifier should equal to: "A"
IServiceB myService = new MyService(); // ServiceIdentifier should equal to: "B"
到目前为止我尝试过:
public class MyService
{
public MyService()
{
if (this is IServiceA)
{
ServiceIdentifier = "A"
}
if (this is IServiceB)
{
ServiceIdentifier = "B"
}
}
}
但这似乎不起作用,因为在这两种情况下它都返回:"A",我想是因为MyService
实现了两个接口,所以 Test()
中的第一个if
参数将始终为真。
我如何在不必使用依赖注入等的情况下处理这个问题?
Edit1:我试图解决的问题是,许多全局参数必须具有不同的值,我希望这些值取决于MyService
实例化的方式,而不必一直将此信息注入其构造函数。
不太清楚你想做什么,但看看显式接口实现。
实现示例:
interface IServiceA
{
void DoSomething();
}
interface IServiceB
{
void DoSomething();
}
class MyService : IServiceA, IServiceB
{
void DoSomething(string parameter)
{
Console.WriteLine("I'm " + parameter);
}
void IServiceA.DoSomething()
{
DoSomething("service A");
}
void IServiceB.DoSomething()
{
DoSomething("service B");
}
}
测试:
void Main()
{
var service = new MyService();
IServiceA serviceA = service;
serviceA.DoSomething();
IServiceB serviceB = service;
serviceB.DoSomething();
}
输出:
我是服务 A
我是服务 B
也许您应该解释您的实际问题是什么,以便找到更好的解决方案。
如果将一个类定义为实现两个接口,则该类的每个实例化都将实现这两个接口。您不会通过将类的引用分配给类型为 IServiceA 或 IServiceB 的变量来更改类实现的内容。如果您有 IServiceA 类型的变量,则只需将可在基础对象中访问的功能/属性限制为定义为 IServiceA 的集合。
目前尚不清楚您在这里要实现的目标,但也许您根本不需要使用接口。如果您只是使用一个属性构造 MyService 对象,该属性指示它是什么类型的服务,并将其保存为私有成员变量,那么您可以在对象生命周期的稍后根据需要通过只读属性访问该成员变量。
正如塞缪尔所说,你不能实例化一个接口。您可以做的是声明接口类型的变量,如下所示:
IServiceA myService;
您可以为其分配实现该接口的任何类型的对象。然后像这样分配变量时(请注意代码中缺少的"new"关键字):
IServiceA myService = new MyService();
您正在将myService
设置为类型 MyService
(这很好,因为MyService
实现了 IServiceA
)。
但是,MyService
的构造函数不知道实例将分配给的变量的类型,因此没有(明智的)方法可以使用构造函数分配给这样的属性。
和IServiceB是相同的,那么你无论如何都会遇到一些问题。假设它们都声明了一个属性:
bool Test { get; set; }
然后在 MyService
或实现这两个接口的任何其他类中,您需要将此属性称为 IServiceA.Test
或 IServiceB.Test
- 我确定这不是您想要做的。
我相信有更好的方法来做你想要实现的目标,但如果你能解释更多背后的动机,这样我们就可以尝试提供帮助,那将是有帮助的。
编辑:
我试图猜测你在追求什么,但看看这个。假设我们定义了一个接口:
public interface IMyService
{
string Name { get; }
}
和两个类:
public class MyServiceA : IMyService
{
public string Name
{
get
{
return "A";
}
}
}
public class MyServiceB : IMyService
{
public string Name
{
get
{
return "B";
}
}
}
然后我们可以编写这样的程序:
private static void Main(string[] args)
{
IMyService testService;
testService = new MyServiceA();
Console.WriteLine(testService.Name); // prints 'A'
testService = new MyServiceB();
Console.WriteLine(testService.Name); // prints 'B'
Console.ReadLine();
}
因此,局部变量 testService
已声明为 IMyService 类型,但可以为其分配 MyServiceA
或 MyServiceB
类型的对象(因为两者都实现了接口)。然后,您可以在不知道该对象的确切类型的情况下调用接口属性Name
,如本例所示,您将根据testService
的实际类型返回"A"或"B"。
我希望这很清楚吗?
编辑 2(在编辑问题之后):
您希望 MyService 根据其实例化的方式具有不同的"状态",但您不想将此信息传递给构造函数?那么,您希望MyService如何知道它应该做什么?
当然,您不必在构造函数中传递所有信息。您可以像这样定义MyService
类:
public class MyService
{
public MyService(string letter)
{
if (letter == "A")
{
this.Name = "Service A";
// Set other property values for service A
}
else if (letter == "B")
{
this.Name = "Service B";
// Set other property values for service B
}
else
{
throw new NotImplementedException();
}
}
public string Name { get; set; }
}
然后像这样编写程序:
private static void Main(string[] args)
{
MyService testService;
testService = new MyService("A");
Console.WriteLine(testService.Name); // prints 'Service A'
testService = new MyService("B");
Console.WriteLine(testService.Name); // prints 'Service B'
Console.ReadLine();
}
因此,通过将一个字符字符串传递给构造函数(并且有更好的方法,这只是一个示例/概念证明),您可以在没有接口的情况下实现您需要做的事情。