Конкретный код структуры Entity Entity Сначала сопоставление модели «много ко двум» - PullRequest
1 голос
/ 17 марта 2011

Я немного растерялся.

В основном у меня есть эти две модели:

public class Player
{
    public int PlayerId { get; set; }
    public string Name { get; set; }

    public virtual ICollection<Game> Games { get; set; }
}

public class Game
{
    public int GameId { get; set; }

    public virtual Player PlayerBlack { get; set; }
    public virtual Player PlayerWhite { get; set; }
}

Теперь схема базы данных, которую EF Code First создает для меня, неверна, потому что игровой стол получает 3 внешних ключа (Playerblack, PlayerWhite и Player) вместо 2.

Итак, как я могу связать эти Модели вместе, чтобы EF понимал, что Игры Игроков находятся по взгляду на Черного или Белого Игрока.

По сути, каждый раз, когда я звоню myPlayer.Games EF должен смотреть на PlayerBlack AND PlayerWhite Foreign Keys.

Возможно ли это вообще?

Ответы [ 2 ]

1 голос
/ 17 марта 2011

Я считаю, что это невозможно. Вы не можете иметь связь с одной конечной точкой на одной стороне и двумя конечными точками на другой стороне отношения.

Возможные обходные пути:

  • Используйте две коллекции в классе Player:

    public virtual ICollection<Game> GamesAsBlackPlayer { get; set; }
    public virtual ICollection<Game> GamesAsWhitePlayer { get; set; }
    

    В зависимости от контекста вы можете объединить эти коллекции в коллекцию только для чтения Games, которая не сопоставлена ​​с базой данных.

(Изменить: Предлагаемый второй обходной путь был дерьмом, сейчас удален.)

Edit2: Еще один обходной путь может заключаться в расширении модели вашего класса дополнительным классом PlayerInGame:

public class Player
{
    public int PlayerId { get; set; }
    public string Name { get; set; }

    public virtual ICollection<PlayerInGame> PlayerInGames { get; set; }

    // optional helper property
    [NotMapped]
    public IEnumerable<Game> Games
    {
        get
        {
            return PlayerInGames.Select(g => g.Game);
        }
    }
}

public class Game
{
    public int GameId { get; set; }
    public virtual ICollection<PlayerInGame> PlayersInGame { get; set; }

    [NotMapped]
    public Player PlayerBlack
    {
        get
        {
            return PlayersInGame.Single(p => p.WhiteOrBlack == "B").Player;
        }
    }

    [NotMapped]
    public Player PlayerWhite
    {
        get
        {
            return PlayersInGame.Single(p => p.WhiteOrBlack == "W").Player;
        }
    }
}

public class PlayerInGame
{
    public int PlayerInGameId { get; set; }

    public virtual Game Game { get; set; }
    public virtual Player Player { get; set; }
    public string WhiteOrBlack { get; set; }
}

Как вы можете видеть методом Single в свойствах PlayerBlack и PlayerWhite в классе Game, вы должны убедиться, что в вашей бизнес-логике созданы правильные PlayerInGame сущности, чтобы ваш * В коллекции 1027 * всегда есть два элемента с черным или белым флагом соответственно.

0 голосов
/ 17 марта 2011

Я бы решил проблему следующим образом:

public abstract class Player
{
    public int ID { get; set; }
}

public class WhitePlayer : Player
{
}

public class BlackPlayer : Player
{
}

public class Game
{
    public int ID { get; set; }

    public virtual WhitePlayer WhitePlayer { get; set; }
    public virtual BlackPlayer BlackPlayer { get; set; }
}

public class GamePlayerContext : DbContext
{
    public DbSet<Game> Games { get; set; }
    public DbSet<Player> Players { get; set; }
}
...