Не совсем. Это просто синтаксический перевод. Например, компилятор переведет это:
var query = from item in source
select item.Property;
в
var query = source.Select(item => item.Property);
Он делает это, ничего не зная о методе Select
. Он просто выполняет перевод, а затем пытается скомпилировать переведенный код.
Все переводы тщательно документированы в разделе 7.16 спецификации C # 4 (и, конечно, эквивалент для более ранних выпусков).
В случае Rx он вызывает расширения на IObservable<T>
и IQbservable<T>
. В случае параллельных расширений он вызывает методы расширения для ParallelQuery<T>
.
Вы можете сделать с ней безумный материал - у меня есть сообщение в блоге , в котором приведено несколько примеров. Вот еще один странный:
using System;
using System.Linq;
namespace CornerCases
{
class WeirdQueryExpression
{
static WeirdQueryExpression Where(Func<int, int> projection)
{
return new WeirdQueryExpression { Select = ignored => "result!" };
}
Func<Func<string, bool>, string> Select { get; set; }
static void Main()
{
string query = from x in WeirdQueryExpression
where x * 3
select x.Length > 10;
Console.WriteLine(query);
}
}
}
Запрос переводится как:
WeirdQueryExpression.Where(x => x * 3)
.Select(x => x.Length > 10);
... который является вызовом статического метода, который возвращает WeirdQueryExpression
, за которым следует доступ к свойству Where
, которое возвращает Func<Func<string, bool>, string>
. Затем мы вызываем этого делегата (передавая другого делегата) и присваиваем результат query
.
фанк, да?