Модель базы данных для объектно-ориентированного проектирования? - PullRequest
7 голосов
/ 07 июля 2011

Как мне разработать классы, скажем, в c # для представления модели базы данных?

С учетом следующих таблиц и полей для базы данных,

Таблица: Сотрудник

Pk EmpID
   Lname
   Fname
   Adress
Fk DeptID

Таблица: Отдел

Pk DeptID
   DeptName
   Location

Хорошо, теперь я хочу сделать 2 класса по C #, один для Сотрудника и один для Отдела.Часть, на которую я зацикливаюсь - это внешние ключи.Должен ли я использовать внешние ключи в своем дизайне для объектов, или я должен добавить ссылку в мой класс Employee отдела, или я должен добавить список ссылок на сотрудников в моем классе Department, или я должен сделать и то, и другое?Я знаю, что если я буду использовать внешние ключи, это будет менее эффективно, потому что мне придется искать в списке первичных ключей, которые соответствуют внешнему ключу, но я, вероятно, должен в любом случае включить их в проект.

Ответы [ 4 ]

3 голосов
/ 06 января 2012

Разработка @Paul Sonier ответ ...

P.S. Я использую бизнес-уровень , бизнес-классы в общем смысле, а не как жаргон какой-то конкретной модели технического дизайна.

Конкретные проблемы использования ключей базы данных
Использование ключей базы данных может привести к взрыву накладных расходов на кодирование для синхронизации объектов и базы данных. По мере необходимости добавлять, изменять, удалять объекты (через пользовательский интерфейс) вы будете прыгать через обручи, как сумасшедшие. Как бы вы создали дочерний объект, если родительский объект еще не существует в базе данных? Представьте себе попытку сделать это с любой структурой данных N-уровня.

Всегда разрабатывать бизнес-классы без учета хранения данных
Классы бизнес-уровня должны точно отражать бизнес-правила, жаргон, концепции и контекст. Загрязнение этого «пространства идей» некоммерческими материалами с подробностями о хранении или отображении данных плохо в долгосрочной перспективе. Услышь меня сейчас и поверь мне позже.

Бизнес-классы, основанные на некоторой конкретной компоновке таблицы базы данных (и ее ключах и т. Д.), Крайне затруднят написание кода для проверки правил, создания надлежащего состояния этих объектов и т. Д. Это на вершине проблемы синхронизации идентификаторов объектов с базой данных.

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

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

Показатели того, что вы все делаете правильно

  1. Можно создать экземпляр бизнес-объекта без существующей базы данных

  2. Каждый объект может ссылаться на своих «детей», не требуя специальных ключей, созданных вне модели бизнес-класса.

  3. Каждый бизнес-объект сам по себе может проверять, применять, помечать и т. Д. все своих собственных правил, даже тривиальные, такие как "не может быть пустым" , Проверка бизнес-правил для составных классов / объектов - это деятельность по разработке и анализу классов, а не деятельность по разработке базы данных.

3 голосов
/ 07 июля 2011

Не используйте «внешние ключи» в ваших объектах. Использовать ссылки; в каждом отделе должен быть список сотрудников. В зависимости от того, нужна ли вам обратная ссылка от сотрудника к его отделу, определите, будет ли сотрудник ссылаться на отдел.

0 голосов
/ 07 июля 2011

Я не хочу упрощать, но если у вас есть свойства навигации от Employee => Department или Department => Employee, то это довольно специфично для ваших приложений.

Однако, как правило,Я склонен ставить навигационные свойства сверху вниз.Это означает, что у меня будут сотрудники Department.Employees, но не Employee.Departments.

Опять же, это относится именно к вам, но кажется маловероятным, что вам когда-нибудь понадобится получить объект Department у каждого сотрудника.Итак, поиск с ключом внутри класса Employee выглядит примерно так:

class Employee {

    public int[] DepartmentIds { get; set; }
    public List<Department> Departments {
        get {
            return YourStaticReference.DepartmentList
                .Where(x => this.DepartmentIds.Contains(x.DepartmentId));
        }
    }
}

Видите?Желаем удачи!

0 голосов
/ 07 июля 2011

Во-первых, если возможно, я бы предложил использовать такой инструмент, как NHibernate, Entity Framework или Linq to SQL, чтобы сделать объектно-реляционное отображение для вас. Но, если вы не хотите этого делать, я, вероятно, разработал бы мою объектную модель так:

public class Employee
{
    public int Id { get; set; }
    public string LastName { get; set; }
    public string FirstName { get; set; }
    public Address Address { get; set; } 
    public Department Department { get; set; }
}

public class Department
{
    public int Id { get; set; }
    public string Name { get; set; }
    public Address Location { get; set; }
    public ICollection<Employee> Employees { get; set; }
}
...