2011-08-11 12 views
5

Próbuję tej klasy:Jeden zero/jeden związek (kod pierwszy)

public class Person 
{ 
    public int PersonID { get; set; } 
    public string Name { get; set; } 
    public int SpouseID { get; set; } 
    public virtual Person Spouse { get; set; } 
} 

Zależność jest: jedna osoba ma jeden lub zero małżonek/ jeden z małżonków wymagane Osoba

Czy można zbudować ten model w Fluent API?

Dzięki.

Odpowiedz

6

Niestety nie jest możliwe stworzenie prawdziwego odnośnika relacji jeden do jednego, ponieważ EF nie obsługuje obecnie unikatowych kluczy. Aby to prawdziwe odniesienie indywidualne jeden na jeden SpouseID musi być oznaczone jako unikatowe. EF zezwala jeden do jednego tylko na klucze podstawowe (klucz podstawowy w obiekcie zależnym musi być również kluczem obcym do jednostki głównej), co oznacza, że ​​samo odniesienie relacji jeden do jednego zakończy się w PersonID <-> PersonID = dwie jednostki o tym samym numerze PersonID w jednej tabeli . Nie jest to możliwe, ponieważ PersonID jest kluczem podstawowym i musi być unikalny.

można obsługiwać go jako jeden-do-wielu i wystawiać tylko jedną właściwość nawigacji jak wiesz:

modelBuilder.Entity<Person>() 
      .HasOptional(p => p.Spouse) 
      .WithMany() 
      .HasForeingKey(s => s.SpouseID); 

Aby wymusić jeden do jednego relacji w bazie danych można dodać custom database initializer i ręcznie tworzyć unikatowe indeks na kolumnie SpouseID.

Problem polega na tym, że jest to tylko jednokierunkowa nawigacja, dzięki czemu można uzyskać współmałżonka osoby, ale z tego nie można wrócić do męża.

+0

Dzięki za pomoc Ladislav – Joao

1

Ta odpowiedź jest sugestią zamiast dokładną odpowiedzią.

W realnym scenariuszu nie jest to poprawny projekt, przede wszystkim każdy współmałżonek ma również współmałżonka, który odnosi się do tej samej osoby, na przykład Oblubienica Małżonki Osoby jest samą Osobą. Modelujemy to w naszej aplikacji jako Osoby i PeronRelacje, PersonRelations mają właściwość FromPersonID, ToPersonID i Type. Typ określa "mąż < -> Wife", "żona < -> mąż", "Ojciec < -> Son", "Syn < -> Ojciec" itd

public class Person{ 
    public int PersonID {get;set;} 
    ... 
    public ICollection<PersonRelations> FromRelations {get;set;} 
    public ICollection<PersonRelations> ToRelations {get;set;} 

} 

public class PersonRelations{ 

    .. 
    public int FromPersonID {get;set;} 
    public int ToPersonID {get;set;} 

    public RelationType Type {get;set;} 
    public Person FromPerson {get;set;} 
    public Person ToPersion {get;set;} 

    // useful for Employment and Marriage 
    // durations 
    public DateTime? Start {get;set;} 
    public DateTime? End {get;set;} 
} 

public enum RelationType{ 
    Husband_Wife, 
    Wife_Husband, 
    Father_Son, 
    Son_Father, 
    Friend_Friend, 
    Employee_Employer, 
    Employer_Employee 
} 

Daje to advantage jak można przechowywać więcej informacji na temat relacji i poruszanie się po nich w obu kierunkach wraz z wieloma zapytaniami.

Każda relacja ma również odpowiednią relację przeciwną. Będziesz musiał napisać dodatkową logikę, aby zachować właściwą odwrotną relację, aby działała poprawnie.

Jest to bardzo łatwe do wdrożenia w Entity Framework, ponieważ jest to prosta relacja One to Many.

Powiązane problemy