相关疑难解决方法(0)

通用约束,其中T:struct和T:class

我想区分以下情况:

  1. 普通值类型(例如int)
  2. 可以为null的值类型(例如int?)
  3. 引用类型(例如string) - 可选地,我不关心这是否映射到上面的(1)或(2)

我已经提出了以下代码,它适用于案例(1)和(2):

static void Foo<T>(T a) where T : struct { } // 1

static void Foo<T>(T? a) where T : struct { } // 2
Run Code Online (Sandbox Code Playgroud)

但是,如果我尝试像这样检测case(3),它就不会编译:

static void Foo<T>(T a) where T : class { } // 3
Run Code Online (Sandbox Code Playgroud)

错误消息是类型'X'已经定义了一个名为'Foo'的成员,它具有相同的参数类型.好吧,不知何故,我无法在where T : struct和之间产生影响where T : class.

如果我删除第三个函数(3),以下代码也不会编译:

int x = 1;
int? y = 2;
string z = "a";

Foo (x); // OK, …
Run Code Online (Sandbox Code Playgroud)

c# generics struct constraints class

50
推荐指数
4
解决办法
5万
查看次数

泛型类型参数和Nullable方法重载

嗨,
我有使用泛型和可空的代码:

// The first one is for class
public static TResult With<TInput, TResult>(this TInput o, 
          Func<TInput, TResult> evaluator)
    where TResult : class
    where TInput : class

// The second one is for struct (Nullable)
public static TResult With<TInput, TResult>(this Nullable<TInput> o, 
          Func<TInput, TResult> evaluator)
    where TResult : class
    where TInput : struct
Run Code Online (Sandbox Code Playgroud)

请注意TInput约束,一个是类,另一个是struct.然后我用它们:

string s;
int? i;

// ...

s.With(o => "");
i.With(o => ""); // Ambiguos method
Run Code Online (Sandbox Code Playgroud)

它会导致Ambiguos错误.但我还有另一对:

public static TResult Return<TInput, TResult>(this TInput o,
          Func<TInput, TResult> evaluator, …
Run Code Online (Sandbox Code Playgroud)

.net c# generics types nullable

9
推荐指数
1
解决办法
624
查看次数

具有约束的泛型方法的重载解决问题

代码示例:

interface IFoo { }
class FooImpl : IFoo { }

static void Bar<T>(IEnumerable<T> value)
    where T : IFoo
{
}

static void Bar<T>(T source)
    where T : IFoo
{
}
Run Code Online (Sandbox Code Playgroud)

任何人都可以解释,为什么这个方法调用:

var value = new FooImpl[0];
Bar(value);
Run Code Online (Sandbox Code Playgroud)

目标Bar<T>(T source)(因此,不编译)?

在解决重载时,编译器是否会考虑类型参数约束?

UPD.

避免与数组混淆.任何实现都会发生这种情况IEnumerable<T>,例如:

var value = new List<FooImpl>();
Run Code Online (Sandbox Code Playgroud)

UPD 2.

@ ken2k提到了协方差.但是,让我们忘掉FooImpl.这个:

var value = new List<IFoo>();
Bar(value);
Run Code Online (Sandbox Code Playgroud)

产生相同的错误.
我敢肯定,之间的隐式转换List<IFoo>IEnumerable<IFoo>存在,因为我可以很容易地写出这样的事情:

static void SomeMethod(IEnumerable<IFoo> sequence) {}
Run Code Online (Sandbox Code Playgroud)

并传入value其中: …

c# generics overload-resolution

5
推荐指数
1
解决办法
603
查看次数