【问题标题】:How to pass generic in an interface (nested generics)如何在接口中传递泛型(嵌套泛型)
【发布时间】:2015-04-23 15:59:24
【问题描述】:

我不知道我是否从正确的角度来解决这个问题,但无论哪种方式我都找不到有效的语法。

我想将 3 种泛型类型传递给一个方法 - 从那里我将在需要时使用反射来创建对象。但是我传递的对象本身就是通用的。

听起来有点像嵌套泛型。

假设我创建了一个接口:

    public interface IAgent<TRequest, TClient, TResponse>
    {
    }

我有一个像这样实现 IAgent 的类:

public class MyClass : IAgent<?>

然后我想调用这样的方法:

public method MyMethod<T>(T obj) where T : IAgent<?>
{
    // do somethings here
}

更新

这是我目前在课堂上所做的。

public sealed class T3Agent
    : AppAgent<T3RequestAdapter, T3WebClient, T3ResponseAdapter>
{
}

public abstract class AppAgent<TRequest, TClient, TResponse>
    where TRequest : IAgentRequestAdapter
    where TClient : CustomWebClient
    where TResponse : IAgentResponseAdapter
{
    public AppResponse Submit(IAppForm appForm, ServiceLog log)
    {
    }
}

public sealed class AppManager
{
    public AppResponse Submit()
    {
        var t3 = new T3Agent();
        var t3Result = t3.Submit(Form, Log);

        return t3Result;
    }
}

在最后一个方法中,我实例化了一个新类(T3Agent),但这与 T3 紧密耦合。我希望能够实例化一次 AppAgent 并通过方法而不是类传递所需的泛型类型,以便我可以重用该类。

【问题讨论】:

  • 我真的不清楚你希望? 在这里做什么......请给我们更多的背景信息。
  • @JonSkeet - 我在“更新”下添加了一些进一步的信息 - 这可能更清楚一点
  • 那么您的Submit 方法会做什么?很可能您想要一个非通用接口以及一个通用接口......
  • 不,submit 的父类目前接受泛型类型,但这意味着每次提交都有一个新类 - 我正在尝试做一些事情 - 1)创建一次类(传递一些不变的参数c'tor),然后使用该方法提交多次,以及 2) 使提交变得容易 - 而不是 submit() - 我想简单地这样做 submit(t1agent) ,其中包含泛型类。
  • 但是提交方法是如何获取请求/响应等的呢?我仍然不清楚你想要实现什么......特别是因为你没有在你的界面中显示任何方法,或者什么会调用它们......

标签: c# generics


【解决方案1】:

我认为你有两个选择:

  1. 如果你必须使用来自 Agent 的泛型类 T,你必须知道类型,所以你必须将它放在你的泛型声明中(参见下面的 TypeNeeded() 方法)
  2. 如果没有必要,则将接口拆分为非通用接口和通用接口,然后让 IAgent 扩展 IAgent (IAgent: IAgent)。现在您可以在不知道 IAgent 类型的情况下创建方法(参见方法 DoSomething())

    public interface IAgent
    {
        void Action( );
        int Calculate( );
    }
    
    public interface IAgent< T > : IAgent
    {
      void Set( T value );
    }
    
    public class MyClass
    {
        public void DoSomething< T >( T agent ) where T : IAgent
        {
            //...
        }
    
        public void TypeNeeded< T, V >( T agent ) where T : IAgent<V>
        {   
        }
    }
    

【讨论】:

    【解决方案2】:

    如果您还不知道泛型接口的类型,那么您的类或方法也需要是泛型的:

    public class MyClass<TRequest, TClient, TResponse> : IAgent<TRequest, TClient, TResponse>
    {
    }
    

    或者对于方法:

    public void MyMethod<T, TRequest, TClient, TResponse>(T obj) where T : IAgent<TRequest, TClient, TResponse>
    {
        // do somethings here
    }
    

    【讨论】:

    • 嗨,不完全是 - 我添加了一个更新,可能会让事情变得更清晰。
    猜你喜欢
    • 2016-02-12
    • 1970-01-01
    • 2023-02-09
    • 2022-11-23
    • 2014-06-03
    • 2021-05-05
    • 2020-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多