Предполагая, что в качестве источника данных у вас есть список анонимного типа, вы можете использовать следующий код для получения свойств выбранного элемента:
dynamic item = comboBox1.SelectedItem;
var id = (int)item.Id;
var name = (string)item.Name;
The 'return this' style is sometimes called a fluent interface and is a common practice.
Мне нравится "свободный синтаксис" и я бы выбрал второй. В конце концов, вы все равно можете использовать его в качестве первого, для людей, которые чувствуют себя неуютно из-за свободного синтаксиса.
Еще одна идея сделать интерфейс, подобный сумматорам, более простым в использовании:
public Adder Add(params int[] i) { /* ... */ }
public Adder Remove(params int[] i) { /* ... */ }
Adder adder = new Adder()
.Add(1, 2, 3)
.Remove(3, 4);
Я всегда стараюсь сделать его коротким и простым. интерфейсы для чтения, но многим нравится писать код настолько сложным, насколько это возможно.
Цепочка - это хорошая вещь, и она является базовой в некоторых средах (например, расширения Linq и jQuery интенсивно ее используют).
Создаете ли вы новый объект или возвращаете это
зависит от того, как вы ожидаете, что ваш исходный объект будет вести себя:
var a = new Adder();
var b = a.Add(4)
.Remove(1)
.Add(7)
.Remove(3);
//now - should a==b ?
Цепочка в jQuery изменит ваш исходный объект - он вернет это. Это ожидаемое поведение - в противном случае в противном случае будут клонированы элементы пользовательского интерфейса.
Цепочка в Linq оставит вашу исходную коллекцию без изменений. Это тоже ожидаемое поведение - каждая связанная функция является фильтром или преобразованием, и исходная коллекция часто неизменна.
Какой шаблон лучше подходит для того, что вы делаете?
Подумайте об этом: если вы вернетесь к этому коду через 5 лет, будет ли это иметь смысл для вас? Если это так, то я полагаю, что вы можете пойти дальше.
Для этого конкретного примера, однако, может показаться, что перегрузка операторов +
и -
прояснит ситуацию и выполнит то же самое.
Для вашего конкретного случая перегрузка арифметических операторов, вероятно, будет лучшим решением.
Возвращение этого
(интерфейса Fluent) является обычной практикой для создания выражений - модульное тестирование и насмешливые рамки используют это много. Свободный Hibernate является еще одним примером.
Возвращение нового экземпляра также может быть хорошим выбором. Это позволяет вам сделать ваш класс неизменным - в общем, хорошая вещь и очень удобная в случае многопоточности. Но подумайте о накладных расходах на создание объекта, если неизменность для вас бесполезна.
Если вы назовете это Adder, я бы с возвращением это вернул. Однако для класса Adder довольно странно содержать ответ.
Вы могли бы подумать о том, чтобы сделать его чем-то вроде MyNumber и создать метод Add () -.
В идеале (IMHO), это не изменит число, хранящееся в вашем экземпляре, но создаст новый экземпляр с новым значением, которое вы возвращаете:
class MyNumber
{
...
MyNumber Add( int i )
{
return new MyNumber( this.Value + i );
}
}
Основное различие между вторым и третьим решением состоит в том, что, возвращая вместо этого новый экземпляр, вы можете «поймать» объект в определенном состоянии и продолжить с этого.
var a = new Adder () .Add (4);
var b = a.Удалить (1);
var c = a.Add (7) .Remove (3);
В этом случае и b, и c имеют захваченное состояние в качестве отправной точки. Я столкнулся с этой идиомой, читая о шаблоне для создания объектов тестовой области в Растущее объектно-ориентированное программное обеспечение, руководствуясь тестами Стива Фримена; Nat Pryce .
На ваш вопрос, касающийся времени жизни ваших экземпляров: я ожидаю, что они будут полезны для сборки мусора, как только вызовы Remove или Add возвращаются.
Я думаю, что для простых интерфейсов "свободно "интерфейс очень полезен, особенно потому, что он очень прост в реализации. Ценность свободного интерфейса в том, что он устраняет много постороннего пуха, который мешает пониманию. Разработка такого интерфейса может занять много времени, особенно когда интерфейс начинает участвовать. Вы должны беспокоиться о том, как использование интерфейса «читает»; На мой взгляд, наиболее убедительным использованием такого интерфейса является то, как он передает намерение программиста, а не количество символов, которые он сохраняет.
Чтобы ответить на ваш конкретный вопрос, мне нравится стиль «вернуть это». Мое типичное использование беглого интерфейса - определить набор опций. То есть я создаю экземпляр класса и затем использую беглые методы в этом экземпляре, чтобы определить желаемое поведение объекта. Если у меня есть опция да / нет (скажем, для ведения журнала), я стараюсь не использовать метод setLogging (bool state), а два метода «WithLogging» и «WithoutLogging». Это немного больше работы, но ясность окончательного результата очень полезна.