自定义实体框架的许多一对多的导航属性 [英] Custom Entity Framework many-to-many navigation property

查看:275
本文介绍了自定义实体框架的许多一对多的导航属性的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有很多一对多映射/数据透视表,我不得不公开为一个实体,以类似以下内容(按这个问题<一的关系进行建模href="http://stackoverflow.com/questions/16273702/model-entity-framework-many-many-plus-shared-relation">Model实体框架多对多加共享关系):

I have a many-to-many mapping/pivot table I had to expose as an Entity in order to model a relationship similar to the following (as per this question Model Entity Framework many-many plus shared relation):

现在,我想为模拟EF集合枚举/添加/删除功能这是一个存量Entity Framework的许多一对多的关系的导航属性present。我将如何做呢?

Now, I would like to emulate the EF collection Enumerate/Add/Remove functionality that is present on the navigation property of a 'stock' Entity Framework many-to-many relationship. How would I do that?

我希望的东西,我可以不吹我的数据表现还算查询。显然,仅仅实现以下弥合透视表没有完成这个目标,也并不遵循EF约定管理系列:

I'm hoping for something that I can still query without blowing my data performance. Obviously just implementing the following to bridge the pivot table doesn't accomplish this goal, and also doesn't follow the EF conventions for managing the collection:

public partial class Composition {
    public IEnumerable<Anthology> Anthologies {
        get {
            return CompositionAnthologies.Select(e => e.Anthology);
        }
    }

    public void AddAnthology(Anthology anthology)
    {
        CompositionAnthologies.Add(new CompositionAnthology() {
            Anthology = anthology,
            Composer = Composer
        });
    }
}

您可以点我一个例子或推荐的出发点? (注意:我使用的是型号为先当前,但将切换到code-第一的解决方案,因为模型首先似乎迅速成为二等公民。)

Can you point me at an example or recommend a starting point? (Note I'm using model-first currently, but would switch to code-first for a solution, since model-first seems to be fast becoming a second-class citizen.)

编辑:。以下是对关系和约束进一步信息

Here's further info on the relationship and constraints.

在许多一对多的关系,有一个结表(CompositionAnthologies),包括具有约束力的ComposerId柱,必要时手动创建的FK关系执行Composition.Composer == Anthology.Composer所有Anthology.Compositions(及组成.Anthologies)。下面是结合表为持有关系:

The many-to-many relationship has a junction table ("CompositionAnthologies") including a binding ComposerId column, with necessary manually-created FK relations to enforce Composition.Composer == Anthology.Composer for all Anthology.Compositions (and Composition.Anthologies). Here is the relation as held by the junction table:

ieThere不得与文集成分,但具有不同的作曲家。

i.e.There must be no Compositions related to Anthologies, but having differing Composers.

推荐答案

下面是我目前的解决方案。仍然是开放的建议,因为这掩盖了IQueryable的,它具有性能后果。它也没有背景信息,所以无法删除结(注意NotImplemented例外)。后一个问题是不是对我非常重要,因为我的数据有,我使用反正删除标志。

Here's my current solution. Still open to suggestions, as this obscures IQueryable, which has performance ramifications. It also doesn't have Context, so cannot delete junctions (notice the NotImplemented exceptions). The latter issue is not terribly important for me, because my data has a deleted flag that I use anyway.

下面是关系的一个侧面。它们是对称的

Here's one side of the relation. They are symmetric.

public partial class Composition {
    public ICollection<Anthology> Anthologies {
        get {
            return new JunctionedAnthologies(this);
        }
    }
}

public class JunctionedAnthologies : ICollection<Anthology> {
    private readonly Composition _parent;

    public JunctionedAnthologies(Composition parent)
    {
        _parent = parent;
    }

    public void Add(Anthology item) {
        if (item.Composer == null) {
            if (_parent.Composer == null) throw new InvalidOperationException("The parent or child Composer must be set to form this association");
            item.Composer = _parent.Composer;
        }
        else if (_parent.Composer == null) {
            _parent.Composer = item.Composer;
        }
        else if (item.Composer != _parent.Composer) {
            throw new InvalidOperationException("The parent and child must not have a differing Composer assigned");
        }
        junction.Add(new CompositionAnthology() {
            Anthology = item,
            Composer = item.Composer
        });
    }

    public void Clear() {
        throw new NotImplementedException();
    }

    public bool Contains(Anthology item) {
        return junction.Any(j => j.Anthology == item);
    }

    public void CopyTo(Anthology[] array, int arrayIndex) {
        throw new NotImplementedException();
    }

    public int Count {
        get { return junction.Count; }
    }

    public bool IsReadOnly {
        get { return false; }
    }

    public bool Remove(Anthology item) {
        throw new NotImplementedException();
    }

    public IEnumerator<Anthology> GetEnumerator() {
        return junction.Select(e => e.Anthology).GetEnumerator();
    }

    IEnumerator IEnumerable.GetEnumerator() {
        return GetEnumerator();
    }

    private ICollection<CompositionAnthology> junction {
        get {
            return _parent.CompositionAnthologies;
        }
    }
}

这篇关于自定义实体框架的许多一对多的导航属性的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆