共用方式為


使用範圍參數的 C# 14 重載解析

C# 14 隨 .NET 10 發布,引進新的 內建範圍轉換和型別推斷規則。 這些變更使得具有範圍參數的多載在更多情況下可應用。

先前的行為

在 C# 13 和更早版本中,採用 ReadOnlySpan<T>Span<T> 接收器的擴充方法不適用於 類型 T[]的值。 因此,只有非 Span 擴充方法,例如來自 System.Linq.Enumerable 類別的方法,通常會系結在 Expression lambda 內。

新行為

在 C# 14 和更新版本中,具有 ReadOnlySpan<T>Span<T> 參數的方法可以參與型別推斷,或在更多案例中當做擴充方法使用。 這讓基於範圍的方法如同 System.MemoryExtensions 類別中的方法在更多情境中系結,包括在 Expression Lambda 表達式中,這在以解譯方式編譯時會導致執行時例外。

引進的版本

.NET 10 Preview 1

中斷性變更的類型

這項變更是 行為上的變化

變更的原因

C# 語言功能允許更簡化的 API 設計和使用(例如,一個 ReadOnlySpan<T> 擴充方法可以同時應用於 Span 和陣列)。

如果您需要繼續使用表達式解譯,請確定非範圍多載已系結,例如,將自變數轉換成方法簽章採用或呼叫擴充方法的確切類型,作為明確的靜態調用:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;

M((array, num) => array.Contains(num)); // fails, binds to MemoryExtensions.Contains
M((array, num) => ((IEnumerable<int>)array).Contains(num)); // ok, binds to Enumerable.Contains
M((array, num) => array.AsEnumerable().Contains(num)); // ok, binds to Enumerable.Contains
M((array, num) => Enumerable.Contains(array, num)); // ok, binds to Enumerable.Contains

void M(Expression<Func<int[], int, bool>> e) => e.Compile(preferInterpretation: true);

受影響的 API