Compartilhar via


Resolução de sobrecarga do C# 14 com parâmetros de intervalos

O C# 14, que é fornecido com o .NET 10, introduz novas conversões de intervalo internas e regras de inferência de tipo. Essas alterações tornam as sobrecargas com parâmetros de intervalo aplicáveis em mais cenários.

Comportamento anterior

No C# 13 e anterior, um método de extensão que usa um receptor ReadOnlySpan<T> ou Span<T> não era aplicável a um valor do tipo T[]. Portanto, apenas métodos de extensão que não se estendem, como os da classe System.Linq.Enumerable, geralmente eram associados dentro de lambdas de Expressão.

Novo comportamento

No C# 14 e posterior, métodos com parâmetros ReadOnlySpan<T> ou Span<T> podem participar da inferência de tipo ou ser usados como métodos de extensão em mais cenários. Isso faz com que métodos baseados em span como os da classe System.MemoryExtensions se associem em mais cenários, incluindo dentro de Expression lambdas, em que eles causarão exceções de tempo de execução quando compilados com interpretação.

Versão introduzida

.NET 10

Tipo de alteração interruptiva

Essa alteração é uma mudança comportamental .

Motivo da alteração

O recurso de linguagem C# permite o design e o uso simplificados da API (por exemplo, um método de extensão ReadOnlySpan<T> pode ser aplicado a intervalos e matrizes).

Se você precisar continuar usando a interpretação de expressões, verifique se as sobrecargas não abrangentes estão associadas, por exemplo, convertendo argumentos para os tipos exatos exigidos pela assinatura do método ou invocando os métodos de extensão como invocações estáticas explícitas.

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);

APIs afetadas