1

次のような関係をモデル化するために、エンティティとして公開する必要のある多対多のマッピング/ピボット テーブルがあります (この質問Model Entity Framework many-many plus shared relationshipに従って):

ここに画像の説明を入力

ここで、'stock' Entity Framework 多対多関係のナビゲーション プロパティに存在する EF コレクションの列挙/追加/削除機能をエミュレートしたいと思います。どうすればいいですか?

データのパフォーマンスを低下させることなくクエリを実行できることを望んでいます。明らかに、ピボット テーブルをブリッジするために次を実装するだけでは、この目標は達成されません。また、コレクションを管理するための EF 規則にも従いません。

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
        });
    }
}

例を挙げたり、出発点を推奨したりできますか? (私は現在モデル ファーストを使用していますが、モデル ファーストは急速に二流市民になりつつあるように見えるため、解決策としてコード ファーストに切り替えることに注意してください。)


編集:関係と制約に関する詳細情報は次のとおりです。

多対多の関係には、すべての Anthology.Compositions (および Composition.Anthology) に対して Composition.Composer == Anthology.Composer を強制するために必要な手動で作成された FK リレーションを含むバインディング ComposerId 列を含むジャンクション テーブル ("CompositionAnthologies") があります。 . ジャンクション テーブルが保持するリレーションは次のとおりです。

ここに画像の説明を入力

つまり、アンソロジーに関連するコンポジションがあってはなりませんが、コンポーザーが異なります。

4

1 に答える 1

0

これが私の現在の解決策です。これにより、パフォーマンスに影響を与える IQueryable がわかりにくくなるため、引き続き提案を受け付けています。また、コンテキストがないため、ジャンクションを削除できません (NotImplemented 例外に注意してください)。後者の問題は、私にとってそれほど重要ではありません。私のデータには、とにかく使用する削除済みフラグがあるからです。

ここに関係の一面があります。それらは対称的です。

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;
        }
    }
}
于 2013-05-02T19:30:44.430 に答える