簡體   English   中英

泛型類型的泛型方法重載不明確

[英]Generic method overload ambiguous with nullable types

假設我有兩種通用的,重載的表單方法:

public string Do<T>(T maybeValue, Func<T, string> func)
  where T : class
{
  if(maybeValue == null) return null;
  return func(maybeValue);
}

public string Do<T>(T? maybeValue, Func<T, string> func)
  where T : struct
{
  if(!maybeValue.HasValue) return null;
  return func(maybeValue.Value);
}

現在,使用類型為nullable的變量調用該方法,C#拒絕編譯並說兩次重載之間的調用是不明確的:

int? maybeX = 3;
Do(maybeX, x => x.ToString());

以下方法或屬性之間的調用不明確:' Program.Do<int?>(int?, System.Func<int?,string>) '和' Program.Do<int>(int?, System.Func<int,string>) '

簡單的修復是在調用方法時包含泛型參數,或指定lambda參數的類型:

Do<int>(maybeX, x => x.ToString());
Do(maybeX, (int x) => x.ToString());

有意思的是,選擇int? 作為調用期間的泛型類型將無法編譯

該類型必須是引用類型,以便在泛型類型或方法中將其用作參數“T”。

怎么會? 顯然,兩個重載中只有一個可以與int?類型的值一起使用int? 但是編譯器說調用是模棱兩可的。 我是否可以進一步約束方法以幫助編譯器決定調用哪個方法,而不必讓調用代碼明確指定類型?

where T : class約束不是方法簽名的一部分。 該檢查稍后在方法過載選擇過程中發生。
這就是為什么它被認為是模棱兩可的。 在檢查任何約束之前,兩種方法都匹配。
如果你明確地說Do<int?>只有第一種方法匹配,但是約束'踢進來'並確定它是無效的,因為int? 不是參考類型。

如果您將其更改為:將選擇第二種方法:

public static string Do<T>(T? maybeValue, Func<T?, string> func)
    where T : struct

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM