假设我有来自两个提供者的两个相同的服务,并且我想编写一段代码,根据客户端请求调用它们中的任何一个。
更清楚地说,我有提供者A和提供者B。客户端将提交对A或B的请求,因此我必须调用它们的类来处理请求。
我创建了provider接口
interface IProviderInterface
{
string GetRedirectUrl();
string GetStatus();
}然后,每个提供程序类都实现了该接口
public class ProviderA: IProviderInterface
{
public ProviderA()
{
}
public string GetRedirectUrl()
{
return "URL for provider A";
}
public string GetStatus()
{
return "Check status with provider A API";
}
}现在,在提供程序管理器类中,我使用switch语句来调用所需的提供程序类。
public class ProvidersManager
{
IProviderInterface ProviderObj;
public ProvidersManager(string ProviderName)
{
switch (ProviderName)
{
case "A":
ProviderObj = new ProviderA();
break;
case "B":
ProviderObj = new ProviderB();
break;
}
}
public string GetRedirectUrl()
{
return ProviderObj.GetRedirectUrl();
}
public string GetStatus()
{
return ProviderObj.GetStatus();
}
}但此方法要求我在每次添加新的提供程序时编辑提供程序管理器类。
我想知道是否有一种方法可以在不更改代码的情况下以更动态的方式调用所需的类。
发布于 2018-10-06 02:27:26
使用DI避免在ProvidersManager中进行更改。
或者,您可以重构此代码并创建一个工厂,该工厂负责为所提供的提供者名称提供provider类型的对象。
发布于 2018-10-06 02:31:21
您可以使用一些替代方案来完成此操作:
泛型类型
public class ProvidersManager<TProvider> where TProvider : IProviderInterface
{
public ProvidersManager() =>
ProviderObj = Activator.CreateInstance<TProvider>();
}
// eg: new ProvidersManager<ProviderA>();使用type (在其他地方加载之前)
public ProvidersManager(Type providerImplementationType) =>
ProviderObj = (IProviderInterface)Activator.CreateInstance(myType);
// eg: new ProvidersManager(typeof(ProviderA));使用类型全名
public ProvidersManager(string providerFullName) =>
ProviderObj = (IProviderInterface)Activator.CreateInstance(Type.Load(providerFullName));
// eg: new ProvidersManager("MyApplication.Common.ProviderA");发布于 2018-10-06 02:32:12
ProviderManager.cs
internal static class ProviderManager
{
private static readonly Dictionary<string, BaseProvider> _providers = new Dictionary<string, BaseProvider>();
public static void Register(string name, BaseProvider provider) => _providers.Add(name, provider);
public static string GetRedirectUrl(string name) => _providers[name].GetRedirectUrl();
public static string GetStatus(string name) => _providers[name].GetStatus();
}BaseProvider.cs
internal abstract class BaseProvider
{
private BaseProvider(string name) => ProviderManager.Register(name, this);
public abstract string GetRedirectUrl();
public abstract string GetStatus();
}ProviderA.cs
internal class ProviderA : BaseProvider
{
private readonly string _redirectUrl;
private readonly string _status;
public ProviderA(string redirectUrl, string status) : base("A")
{
_redirectUrl = redirectUrl
_status = status;
}
public string GetRedirectUrl() => _redirectUrl;
public string GetStatus() => _status;
}使用
internal class Program
{
public static void Main(string[] args)
{
ProviderA providerA = new ProviderA("http://stackoverflow.com", "active");
string url = ProviderManager.GetRedirectUrl("A");
}
}希望这能有所帮助。
https://stackoverflow.com/questions/52671285
复制相似问题