Абсолютно новый для моделирования предметной области, не знаю с чего начать - PullRequest
4 голосов
/ 23 сентября 2009

Я начинаю новый проект и хочу начать с моделирования данных, которые клиент должен хранить. Тем не менее, я понятия не имею, с чего начать. Пока что я пытаюсь смоделировать две простые сущности, Event и Address. Event может иметь несколько Addresses, а Address может быть связано с несколькими Events. Вот что у меня есть:

public class Event
{
    public int Id { get; set; }
    public string Name { get; set; }
    public string Description { get; set; }
    public List<Address> Addresses { get; set; }
}

public class Address
{
    public int Id { get; set; }
    public string Street { get; set; }
    public string Zip { get; set; }
    public List<Event> Events { get; set; }
}

Однако я столкнулся с проблемой, когда попытался создать тестовые репозитории для этих двух объектов. Они имеют циклическую зависимость: Event не может заполнить свой список Addresses, пока Address не заполнится полностью, но Address не может заполнить свой список Events, пока Events не будет заполнен полностью. Это заставило меня поверить, что я не знаю, что делаю.

Я много читал о POCO, DTO, DAO и DDD, но эти концепции не имеют для меня большого смысла, независимо от того, как сильно я пытаюсь их понять. Я только недавно закончил колледж и даже не слышал о термине «модель предметной области» до недели назад.

Концептуально, я хотел бы сначала создать классы, представляющие типы данных, которые мне нужно хранить (Entities, я полагаю). Эти классы также будут содержать логику проверки (это POCO?). После этого я хочу настроить репозитории для доступа к коллекциям этих объектов и заполнить любые отношения, которые они могут иметь (например, Event будет заполнен списком Addresses) [это постоянное невежество?]. Только после всего этого я хочу создать базу данных для хранения данных (через DAO? Является ли ORM DAO? Как бы я использовал LINQ-To-SQL для этого?). И где IoC вписывается во все это или не подходит вообще, если я знаю, что мой бэкэнд никогда не изменится, и я всегда буду использовать только одну базу данных?

Если это еще не было очевидно, я довольно озадачен тем, с чего начать. У меня есть хорошее концептуальное представление о том, что я хочу сделать, я просто не знаю, как это реализовать. Может ли кто-нибудь дать мне совет относительно хорошей отправной точки? Спасибо.

Ответы [ 3 ]

4 голосов
/ 23 сентября 2009

Что ж, в приведенном вами примере кажется, что Адрес не должен содержать ссылку на события, но вам понадобится репозиторий, который может находить события для данного адреса. Адрес выглядит как объект Value. Существует книга Эрика Эванса , части которой доступны в режиме онлайн, если вы хотите посмотреть, что представляют собой объекты-ценности и чем они отличаются от объектов-сущностей.

Что касается контейнеров IOC, то они весьма полезны для устранения заводского кода котельной плиты, когда фабрика отвечает за создание ваших объектов для вас. Когда у вас есть контейнер IOC, разработчик запрашивает у контейнера экземпляр класса, который вам нужен. Это избавляет вас от необходимости самим писать фабрику.

Невежество в отношении постоянства, насколько я понимаю, состоит в том, что объект не заботится о постоянстве, и именно там находится шаблон хранилища. Вы используете хранилище в качестве средства для получения, сохранения, обновления и удаления объектов. Сами объекты не заботятся о своем упорстве.

Я бы смотрел на POCO (обычный старый объект CLR) как на объект, который имеет поведение, но не занимается сквозными проблемами. DTO (объект передачи данных), как правило, представляет собой объект, который практически не имеет поведения, и целью которого является перенос данных из точки A в точку B. DAO (объект доступа к данным) используется для доступа к данным из базы данных, т.е. из репозитория. DDD (Domain Driven Design) - это набор принципов проектирования, которые ведут вас через правильный процесс проектирования, когда вы думаете о своем программном обеспечении с точки зрения области, для которой вы его строите.

Надеюсь, это поможет.

0 голосов
/ 23 сентября 2009

Не беспокойтесь о буквах закона с самого начала.

Есть несколько основных принципов, которые привели к алфавитному шаблону и методологиям, и если вы будете придерживаться этих принципов, вы увидите, что ваш код тяготеет к, по крайней мере, некоторым из них большую часть времени.

Если вы обеспокоены закономерностями и концепциями, касающимися фактического решения вашей проблемы, вы рискуете выбрать шаблон, который будет идеальным решением проблемы, отличной от той, которая у вас есть.

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

Как вы можете смоделировать это так, чтобы остальная часть вашего кода, любые настоящие и будущие требования, с которыми столкнется ваше приложение, могла легко и надежно работать с этими двумя вещами? Для ваших конкретных потребностей, какое решение будет best ?

Сначала подумайте об этом, и вы часто можете обнаружить, что ваше решение похоже на хорошо известный шаблон.

0 голосов
/ 23 сентября 2009

Как указывает Майкл, Address - это «объект значения» во многих доменах, но я собираюсь предположить, что у вас есть совершенно веские аргументы для того, чтобы сделать его «Entity» (идентификатор) и «Aggregate Root» ( хранилище).

Я сам пользователь NHibernate и не знаю всех деталей Linq-to-SQL. Хотя NHibernate поддерживает сопоставления «многие ко многим», настоятельно рекомендуется, чтобы вы (если я правильно помню из Hibernate в действии) включили класс ассоциации (то есть класс, представляющий вашу справочную таблицу) в модель вашего домена.

Вещи становятся более явными, и будущие свойства ассоциации, например, флаг для основного адреса, гораздо проще добавить.

Имея новую модель (Event (1) - (x) EventAddress (x) - (1) Address), помните, что вы должны самостоятельно вести учет двунаправленных ассоциаций, например, следуя паттерну «ведущий-ведомый» Фаулера из UML Distilled.

С помощью NHibernate вы также сообщаете ему, какой конец является обратным (ведомым), но вам нужно будет обратиться к документации Linq-to-SQL, чтобы узнать, как он выполняет тот же трюк.

Подробнее об отношениях «ведущий-ведомый» можно прочитать здесь: http://blog.lowendahl.net/?p=88

...