package turin.relations; import java.util.HashMap; import java.util.LinkedList; import java.util.List; import java.util.Map; public class OneToManyRelation<A, B> implements Relation<A,B> { private Map<A, List<B>> byEndpointA = new HashMap<>(); private Map<B, A> byEndpointB = new HashMap<>(); private Map<B, Subset> bSubsets = new HashMap<>(); public Subset newBSubset() { return new Subset(); } public void link(A endpointA, B endpointB, Subset bSubset) { link(endpointA, endpointB); bSubsets.put(endpointB, bSubset); } @Override public void link(A endpointA, B endpointB) { if (areLinked(endpointA, endpointB)) { return; } if (byEndpointB.containsKey(endpointB)) { unlink(byEndpointB.get(endpointB), endpointB); } if (!byEndpointA.containsKey(endpointA)) { byEndpointA.put(endpointA, new LinkedList<B>()); } byEndpointA.get(endpointA).add(endpointB); byEndpointB.put(endpointB, endpointA); } @Override public void unlink(Object endpointA, Object endpointB) { byEndpointA.get(endpointA).remove(endpointB); byEndpointB.remove(endpointB); bSubsets.remove(endpointB); } @Override public boolean areLinked(Object a, Object b) { if (byEndpointB.containsKey(b)) { return byEndpointB.get(b).equals(a); } else { return false; } } public ReferenceSingleEndpoint getReferenceForB(B b) { return new ReferenceSingleEndpoint(b, byEndpointB, this); } public ReferenceSingleEndpoint getReferenceForSubsetB(B b) { return new ReferenceSingleEndpoint(b, byEndpointB, this); } public ReferenceMultipleEndpoint getReferenceForA(A a) { return new ReferenceMultipleEndpoint(a, byEndpointA, this); } public ReferenceMultipleEndpoint getReferenceForA(A a, Subset subset) { return new ReferenceMultipleEndpoint(a, byEndpointA, this, bSubsets, subset); } }