Использование DTO — это лишь один из частных случаев в разработке.
Хотелось бы акцентировать внимание на том, что помимо сериализации библиотека предназначена для более широкого круга задач.
К примеру, имеется два DTO объекта, и их нужно сравнить. Можно, конечно, написать свою логику сравнения, но проще и быстрее сделать сопоставление снимков, как показано в статье.
Такой вышколенный текст — Вам бы редактором журнала работать =)
Ясно чувствуется, что статью долго и очень усердно воплощали, временами, я бы сказал, дотошно, поэтому и добавить-то особенно нечего.
Но будьте осторожны с этим впредь, ведь как вы и упомянули, программистов пугает такая дотошность руководства, когда не остаётся места для творческого самовыражения…
А как раз-таки именно творческий подход, на мой взгляд, порой подсказывает в программировании самые неожиданные архитектурные решения, до которых заранее, ну, никак не дойдёшь, только в самом процессе и итеративно.
Каким бы ни было ужасным явление Code Behind, стоит признать, что в некоторых ситуациях его применение уместно. Конечно, тут важно не переусердствовать, поэтому ответственность лежит на разработчике.
Представленный в статье «трюк» позволяет обойти некоторые ограничения при выполнении привязок. Безусловно, когда мы получаем больше свободы стоит помнить о безопасности, однако и возможности наши возратают.
Согласен, что такие ситуации скорее исключение из правил, но в то же время они очень «неудобные».
В примере свойство Text привязывается к свойству Number вью-модели через конвертер, но по условию к этому числу нужно добавить заголовок окна приложения.
Если мы будем делать дополнительное свойство Title во вью-модели, то она будет загрязняться интерфейсным кодом, а также придётся использовать что-то вроде MultiBinding, который, кстати, не на всех платформах поддерживается, плюс создавать IMultiValueConverter. Всё довольно усложняется несмотря на тривиальность задачи. С Inline Converter выглядит просто и понятно.
Также может возникнуть и другая ситуация: основная привязка свойства Text должна идти к свойству Number во вью-модели, но, например, в зависимости от нескольких других различных значений свойств этой вью модели, сама строка должна декорироваться тем или иным образом. Поскольку в обычном конвертере у нас нет доступа к самой вью-модели, приходится искать обходные пути, не всегда красивые. В нашем же случае есть прямой доступ к контесту данных представления, нужной нам вью-модели и всем её свойствам.
Думал над вашим вопросом, и пришёл к выводу, что, возможно, не совсем вас понял.
Вы имеете в виду удаление элементов из строки во время работы XAML-дизайнера среды разработки?
Просто в статье описан механизм динамической смены состояния Grid именно во время работы приложения…
Это может быть полезным для сложных интерфейсов, например, когда приложение поддерживает портретную и альбомную ориентацию, и в зависимости от неё визуальные элементы нужно компоновать слегка по-разному, а создавать новую страницу с дублирующимся кодом не имеет смысла.
Правильнее, на мой взгляд, установить у ненужного элемента свойство Visibility в состояние Collased, либо же использовать ItemsControl. Даже если вы удалите строку номер два, то сам контрол останется в визуальном дереве и код останется засорён, если это можно так назвать.
Хотелось бы иметь возможность указывать номер строки/столбца не абсолютно, а как-нибудь относительно.
В статье описан сам принцип и базовый синтаксис, усовершенствовать реализацию можно как угодно, на что хватит фантазии :)
Скажите, вы пробовали заново переопубликовывать ваши игры, но под другими названиями? Только предварительно подготовившись…
Например, можно использовать старую базу пользователей и попросить их обновиться до свежей версии вручную, как раз в тот момент, когда вы опубликуете апдейт, но уже как новое приложение. Опыт на Windows Phone показывает, что если не воспользоваться сполна первыми неделями сразу после публикации, то никакими вменяемыми действиями и крутыми апдейтами уже ситуацию с приложением не выправишь. Шансы попасть в какой-либо топ максимальны лишь сразу после публикации, а потом крайне резко снижаются.
Замечу насчёт композиции функций, что SkipByRing(x).TakeByRing(y) в кольцевом обобщении не равнозначно SliceByRing(x,y), хотя в простых случаях, когда нет полного обхода кольца, они дают идентичный результат.
Так может надо подумать немножко дольше, чтобы недочетов не было?
Тогда бы я отвечал на ваши комментарии раз в день и прогресс шёл значительно медленнее.
Кстати, придумал практическое приложение методам Ring и Turn. К примеру, вы делаете UI, и у вас есть коллекция-заглушка с n-элементами, вдруг вы захотели проверить, как работает UI при 2n, 3n, ...mn элементах. Вам достаточно написать что-то вроде Items = _testItems.Ring(0, m).ToList() и всё.
Решения я генерирую в реальном времени, поэтому появление недочётов вполне закономерно.
Вы можете предложить свои оптимизации, мне самому интересно. Менять тип возвращаемого значения я не вижу смысла, так как сам метод Ring внутри срабатывает за O(1), а на выходе при необходимости можно сделать как ToList(), так и ToArray().
Также придумал последнее обобщение с количеством оборотов =)
public static IEnumerable<T> Turn<T>(this IList<T> items, int skip, int turnsCount = 0)
{
var reverse = skip < 0;
var count = items.Count;
skip = reverse ? count + skip : skip;
var take = turnsCount == 0
? reverse ? -skip - 1 : count - skip
: count*turnsCount;
return items.Ring(skip, take);
}
Если число оборотов 0, то берётся срез от элемента до конца либо в обратном направлении до начала коллекции, в зависимости от типа отсчёта.
Если число оборотов не 0, то берётся несколько оборотов от элемента в прямом либо обратном направлении, в зависимости от знака числа оборотов.
Конечно, у вас может быть своё мнение, но я сторонник написания одного метода пригодного для решения обобщённой задачи, чем нескольких методов для каждого родственного частного случая.
Понимаю, что в обобщённой версии есть несколько дополнительных булевых проверок, но всё же их влияние не столь велико на производительность.
Разве что
var index = reverse ? skip - j : skip + j;
в цикле, возможно, имеет смысл разделить на два цикла, хотя это лучше проверить на практике.
ToList я делаю лишь для того, чтобы сэкономить строчки кода в тестовом примере и только (встроенный метод ForEach() есть только у List), поэтому он здесь не обязателен.
Если изложенный метод и нарушает функциональную композицию, то вы можете скрыть (инкапсулировать) его, а предоставить несколько открытых методов-обёрток, которые работают на обобщённом алгоритме, поэтому сам алгоритм нисколько не теряет своей ценности.
Меня больше интересуют не сами слайсы, а обобщённые алгоритмы. Как вам такая реализация?
В ней слайсы и сдвиги лишь частные случаи колец с прямым и обратным обходом.
Хорошо, соглашусь, что с флагами нужно быть осторожным.
Обдумал идею насчёт длины в качестве второго параметра, и понимаю, что это отличный подход. В статье я взял за ориентир индексацию слайсов языка Питон, что наложило некоторые ограничения. С длиной же можно вывести ещё дополнительный ряд обобщений, например, проходить коллекцию по несколько раз и копировать её, а также использовать отрицательную длину для обхода в обратном направлении.
var letters = new [] {'A', 'B, 'C', 'D'};
letters.Slice(1, 9); // BCDABCDAB
letters.Slice(-2, -9); // CBADCBADC
При создании регулярного выражения мы можем указать флаг RegexOptions.IgnoreCase, вместе с тем можем не указывать, а использовать inline characteri — результат тот же.
Конечно, если вы видите другие пути к консистентности, то можете их предложить, я со своей колокольни рассуждаю :)
Хотелось бы акцентировать внимание на том, что помимо сериализации библиотека предназначена для более широкого круга задач.
К примеру, имеется два DTO объекта, и их нужно сравнить. Можно, конечно, написать свою логику сравнения, но проще и быстрее сделать сопоставление снимков, как показано в статье.
Ясно чувствуется, что статью долго и очень усердно воплощали, временами, я бы сказал, дотошно, поэтому и добавить-то особенно нечего.
Но будьте осторожны с этим впредь, ведь как вы и упомянули, программистов пугает такая дотошность руководства, когда не остаётся места для творческого самовыражения…
А как раз-таки именно творческий подход, на мой взгляд, порой подсказывает в программировании самые неожиданные архитектурные решения, до которых заранее, ну, никак не дойдёшь, только в самом процессе и итеративно.
Спасибо за труд и литературность материала!
Но, на мой взгляд, лучше использовать универсальный способ для решения обширного круга проблемных ситуаций, чем каждый раз изобретать новый хак.
Представленный в статье «трюк» позволяет обойти некоторые ограничения при выполнении привязок. Безусловно, когда мы получаем больше свободы стоит помнить о безопасности, однако и возможности наши возратают.
В примере свойство Text привязывается к свойству Number вью-модели через конвертер, но по условию к этому числу нужно добавить заголовок окна приложения.
Если мы будем делать дополнительное свойство Title во вью-модели, то она будет загрязняться интерфейсным кодом, а также придётся использовать что-то вроде MultiBinding, который, кстати, не на всех платформах поддерживается, плюс создавать IMultiValueConverter. Всё довольно усложняется несмотря на тривиальность задачи. С Inline Converter выглядит просто и понятно.
Также может возникнуть и другая ситуация: основная привязка свойства Text должна идти к свойству Number во вью-модели, но, например, в зависимости от нескольких других различных значений свойств этой вью модели, сама строка должна декорироваться тем или иным образом. Поскольку в обычном конвертере у нас нет доступа к самой вью-модели, приходится искать обходные пути, не всегда красивые. В нашем же случае есть прямой доступ к контесту данных представления, нужной нам вью-модели и всем её свойствам.
Вы имеете в виду удаление элементов из строки во время работы XAML-дизайнера среды разработки?
Просто в статье описан механизм динамической смены состояния Grid именно во время работы приложения…
Это может быть полезным для сложных интерфейсов, например, когда приложение поддерживает портретную и альбомную ориентацию, и в зависимости от неё визуальные элементы нужно компоновать слегка по-разному, а создавать новую страницу с дублирующимся кодом не имеет смысла.
Конечно, у вас своё видение, но, по-моему, он стал компактнее в разы да и сложность его не такая высокая :)
В статье описан сам принцип и базовый синтаксис, усовершенствовать реализацию можно как угодно, на что хватит фантазии :)
Например, можно использовать старую базу пользователей и попросить их обновиться до свежей версии вручную, как раз в тот момент, когда вы опубликуете апдейт, но уже как новое приложение. Опыт на Windows Phone показывает, что если не воспользоваться сполна первыми неделями сразу после публикации, то никакими вменяемыми действиями и крутыми апдейтами уже ситуацию с приложением не выправишь. Шансы попасть в какой-либо топ максимальны лишь сразу после публикации, а потом крайне резко снижаются.
Тогда бы я отвечал на ваши комментарии раз в день и прогресс шёл значительно медленнее.
Кстати, придумал практическое приложение методам Ring и Turn. К примеру, вы делаете UI, и у вас есть коллекция-заглушка с n-элементами, вдруг вы захотели проверить, как работает UI при 2n, 3n, ...mn элементах. Вам достаточно написать что-то вроде Items = _testItems.Ring(0, m).ToList() и всё.
Удобно же, не находите? )
Вы можете предложить свои оптимизации, мне самому интересно. Менять тип возвращаемого значения я не вижу смысла, так как сам метод Ring внутри срабатывает за O(1), а на выходе при необходимости можно сделать как ToList(), так и ToArray().
Также придумал последнее обобщение с количеством оборотов =)
Если число оборотов 0, то берётся срез от элемента до конца либо в обратном направлении до начала коллекции, в зависимости от типа отсчёта.
Если число оборотов не 0, то берётся несколько оборотов от элемента в прямом либо обратном направлении, в зависимости от знака числа оборотов.
Понимаю, что в обобщённой версии есть несколько дополнительных булевых проверок, но всё же их влияние не столь велико на производительность.
Разве что
в цикле, возможно, имеет смысл разделить на два цикла, хотя это лучше проверить на практике.
Если изложенный метод и нарушает функциональную композицию, то вы можете скрыть (инкапсулировать) его, а предоставить несколько открытых методов-обёрток, которые работают на обобщённом алгоритме, поэтому сам алгоритм нисколько не теряет своей ценности.
В ней слайсы и сдвиги лишь частные случаи колец с прямым и обратным обходом.
Обдумал идею насчёт длины в качестве второго параметра, и понимаю, что это отличный подход. В статье я взял за ориентир индексацию слайсов языка Питон, что наложило некоторые ограничения. С длиной же можно вывести ещё дополнительный ряд обобщений, например, проходить коллекцию по несколько раз и копировать её, а также использовать отрицательную длину для обхода в обратном направлении.
При создании регулярного выражения мы можем указать флаг RegexOptions.IgnoreCase, вместе с тем можем не указывать, а использовать inline character i — результат тот же.
Конечно, если вы видите другие пути к консистентности, то можете их предложить, я со своей колокольни рассуждаю :)