Как заставить тип делегата не содержать никакой информации? - PullRequest
1 голос
/ 22 марта 2012

Я разрабатываю API, очень сравнимый с Linq (это linq, который работает с более сложными объектами), и у меня есть несколько разработчиков-клиентов, которые не совсем понимают философию. Я хотел бы помешать им делать некоторые вещи, чтобы их код больше соответствовал тому, что представляет собой API. Так что для примеров я буду просто ссылаться на Linq.

Короче говоря, то, что я вижу в клиентском коде, выглядит примерно так:

IEnumerable<double> xlist;
IEnumerable<double> ylist;
var zlist = xlist.Select( (x,i) => x + ylist.ElementAt(i) );

Это действительно плохо, и вместо того, чтобы говорить людям, что они плохо себя ведут, я хотел бы заставить своих клиентов написать это:

var zlist = xlist.Zip(ylist, (x,y) => x + y);

Поэтому, подумав об этом, я решил, что мне действительно хотелось бы, чтобы мой API не позволял клиентам «вводить» данные в типы делегатов. Другими словами, я хотел бы определить методы расширения, такие как:

IEnumerable<TResult> MySelect<TSource, TResult>(
                                this IEnumerable<TSource> source,
                                StaticFunc<TSource, int, TResult> selector)

где StaticFunc - это какой-то тип делегата, который не содержит никаких данных (или, самое большее, только данные статического контекста).

Может кто-нибудь увидеть способ сделать это?

Ответы [ 2 ]

3 голосов
/ 22 марта 2012

Я разрабатываю API, очень сравнимый с Linq (это linq, который работает с более сложными объектами), и у меня есть несколько разработчиков-клиентов, которые не совсем понимают философию. Я хотел бы помешать им делать некоторые вещи, чтобы их код больше соответствовал тому, что представляет собой API.

Похоже, что вам действительно нужно, это обзор кода и обучение, а не инструменты. В языке нет ничего, чтобы убедиться, что разработчик этого не делает - и вы даже не захотите, IMO. Например, ваше правило запрещает:

public IQueryable<Person> FindUsersByFirstName(string firstName)
{
    return repository.Users.Where(user => user.FirstName == firstName);
}

В конце концов, firstName - это контекстные данные ... но это совершенно соответствует LINQ.

0 голосов
/ 22 марта 2012

Вы можете попытаться использовать Деревья выражений вместо делегатов. Вы сможете проверить, что передается в ваш код, в отличие от делегатов.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...