Func委托给声明的方法

时间:2013-07-15 19:28:12

标签: c# generics func

在非泛型类中声明这两个方法,它们共享相同的签名:

    private TypeResolverResult<T> TryRetrieveFromReusable<T>(TypeResolverConfiguration<T> typeResolverConfiguration) where T : class 
    {
        return null;
    }

    private TypeResolverResult<T> BuildNew<T>(TypeResolverConfiguration<T> typeResolverConfiguration) where T : class
    {
        return null;
    }

如何创建代表这些方法签名的委托?

我似乎无法得到它,我试过了:

    private Func<TypeResolverConfiguration<T>, TypeResolverResult<T>> _typeResolveFunc;

但显然这不起作用,因为该类是非泛型的,我不能改变它。

由于

更新

这或多或少是我需要的:

    public class Manager : ATypeResolver, IManager
    {
        private neeedDelegate;


        public Manager(RuntimeConfiguration runtimeConfiguration, IList<RepositoryContainer> repositories)
        {
            if (runtimeConfiguration.WhatEver)
            {
                neeedDelegate = TryRetrieveFromReusable;
            }
            else
            {
                neeedDelegate = BuildNew;
            }
        }

        public override TypeResolverResult<T> Resolve<T>() where T : class
        {
            //Want to avoid doing this:

            if (runtimeConfiguration.WhatEver)
            {
                TryRetrieveFromReusable(new TypeResolverConfiguration<T>());
            }
            else
            {
                BuildNew(new TypeResolverConfiguration<T>());
            }

            //and have just this

            neeedDelegate<T>(new TypeResolverConfiguration<T>());
        }

        private TypeResolverResult<T> TryRetrieveFromReusable<T>(TypeResolverConfiguration<T> typeResolverConfiguration) where T : class 
        {
            return null;
        }

        private TypeResolverResult<T> BuildNew<T>(TypeResolverConfiguration<T> typeResolverConfiguration) where T : class
        {
            return null;
        }
    }

2 个答案:

答案 0 :(得分:1)

更新从我所看到的情况来看,只要ATypeResolver where T : class Resolve<T>上有public class Manager : ATypeResolver, IManager { private bool tryRetrieveFromReusable; public Manager(RuntimeConfiguration runtimeConfiguration, IList<RepositoryContainer> repositories) { this.tryRetrieveFromReusable = runtimeConfiguration.WhatEver; } public override TypeResolverResult<T> Resolve<T>() { var typeResolver = tryRetrieveFromReusable ? (TypeResolver<T>)TryRetrieveFromReusable : BuildNew; return typeResolver(new TypeResolverConfiguration<T>()); } } ,就可以使用这样的方法:

Func

这使用自定义委托类型(您应该使用的public delegate TypeResolverResult<T> TypeResolver<T>( TypeResolverConfiguration<T> typeResolverConfiguration) where T : class; ):

var typeResolver = ...

如果您愿意,可以将Resolve行移动到自己的方法,将逻辑分开并允许您从return GetTypeResolver<T>()(new TypeResolverConfiguration<T>());以上使用它。如果您这样做,Resolve可能就像:{{1}}。

一样简单

答案 1 :(得分:0)

您似乎并不完全了解泛型的工作原理。我将简要介绍一下,但请阅读MSDN

当你有一个泛型类

public class Foo<T>
{
    public T Bar {get; set;}
}

你使用类似这样的东西

Foo<int> intFoo = new Foo<int>();
Foo<string> stringFoo = new Foo<string();

在编译时,编译器将检测泛型类型的两种用法。它将创建每种用法的类型。所以你的程序集会有类似这样的类型(不完全没有,但让我们假装玩,以便人类可以理解)。

public class FooInt
{
    public int Bar { get; set; }
}

public class FooString
{
    public string Bar { get; set; }
}

它会将Foo<int>FooIntFoo<string>的所有用途替换为FooString

现在,如果我们有一个带泛型方法的非泛型类

public class Foo
{
    public T GetBar<T>() { ..... }
}

你就像这样使用它

Foo foo = new Foo();
int x = foo.GetBar<int>();
string s = foo.GetBar<string();

编译器将生成

public class Foo
{
    public int GetBarInt() { ..... }
    public string GetBarString() { ..... }
}

它会将GetBar<T>替换为GetBarInt,将GetBar<string>替换为GetBarString

但是字段不是那样的。如果你有一个类似的课程

public class Foo
{
    public T Bar;
}

你不能这样做

Foo foo = new Foo();
foo.Bar<int> = 1;
foo.Bar<string> = "test";

编译器只是不明白。我不是内部的专家,但我的猜测是,因为这指向内存中的一个位置,编译不能在编译时生成泛型用法。

但我想说的是这个。泛型不是一些神奇的“我不需要指定类型”功能。它们是编译中的提示,说“我将多次执行同样的操作,我希望您为我生成代码。”