2

假设我在一个名为“接口”的项目中有一个这样的接口:

public interface TestInterface
{
    string Operation();
}

和实现它的类。该类位于另一个项目“类”中:

public class TestClass : TestInterface
{
    public TestClass() { }

    public string Operation()
    {
        return "This is an Operation";
    }
}

我的客户做了这样的事情(这又在另一个项目“客户”中):

class Program
{
    static void Main(string[] args)
    {
        TestInterface i = new TestClass();
        i.Operation();
    }
}

我的问题与这一行有关:

TestInterface i = new TestClass();

通过添加这一行,我实际上被迫从我的“客户端”项目中添加对“接口”和“类”项目的引用。那么为什么要大惊小怪呢?我不能直接引用“类”而不保留“接口”吗?有没有办法仅通过接口访问方法(不引用实现类)?我在这里错过了什么吗?

4

5 回答 5

2

有没有办法只通过接口访问方法

就在这里。TestClass您可以在不引用它的情况下动态加载程序集,通过创建其实例Activator.CreateInstance并将其转换为接口类型:

var assembly = Assembly.Load(...);
var typeFromAssembly = assembly.GetTypes()...;
var myInterfaceVar = (TestInterface)Activator.CreateInstance(typeFromAssembly);

...或者...您可以使用现有的 DI 框架之一(例如 MEF)并以更正确的方式做同样的事情:

[Import]
private TestInterface myInterfaceField;

或者:

var myInterfaceVar = compositionContainer.GetExportedValue<TestInterface>();

根据您喜欢的方式,您可以提出更具体的问题。

于 2013-01-24T10:03:55.223 回答
0

在那个特定的样本中,没有优势。

但是想象一个方法:

public void Foo(ITestInterface handler)
{
    handler.Operation();
}

现在,Foo只对接口进行操作,并不关心什么具体的类实现了这个接口。您现在可以使用或Foo的实例调用,它可以在不同的程序集中定义。TestClassTestClass2

于 2013-01-24T10:05:21.993 回答
0

您可以通过使用 IOC 来实现您所描述的行为。 Unity是一个依赖注入容器,它允许在不手动创建实例的情况下创建实例。

例如,如果您要将类和接口注册到 unity,您将直接使用该接口;

TestInterface i = Container.Resolve<TestInterface>();
于 2013-01-24T10:05:31.230 回答
0

你有界面,所以你的应用程序可以有plug in's..

因此,基本上您您的接口 dll 共享给任何想要为您的应用程序制作插件应用程序的人,然后您可以将该新插件类强制转换为接口并在其上调用方法..

如果您不将类转换为界面,那么您究竟要如何使插件类为您的应用程序工作..

于 2013-01-24T10:10:35.430 回答
0

使您的代码完全独立于TestInterface使用Dependency Inversion的实现。这可以通过一些依赖注入框架来实现。

例如,使用Unity,您可以通过 xml 配置实现

<register type="TestInterface" 
          mapTo="Foo.Bar.TestClass, Foo.Bar" />

而且您的代码将仅依赖于 Unity(不引用实现):

TestInterface i = Container.Resolve<TestInterface>();
于 2013-01-24T10:04:47.257 回答