public static EntityQuad ToEntityQuad(this VDS.RDF.Triple triple, EntityId id)
 {
     return(new EntityQuad(
                id,
                triple.Subject.ToNode(id),
                triple.Predicate.ToNode(id),
                triple.Object.ToNode(id),
                Node.ForUri(triple.GraphUri)));
 }
Beispiel #2
0
 /// <summary>
 /// Returns whether the Store contains the given Triple within the Query Triples
 /// </summary>
 /// <param name="t">Triple to search for</param>
 /// <returns></returns>
 public bool Contains(Triple t)
 {
     return(this._graphs.Any(g => g.Triples.Contains(t)));
 }
 /// <summary>
 /// Gets whether the collection contains the given Triple
 /// </summary>
 /// <param name="t">Triple</param>
 /// <returns></returns>
 public override bool Contains(Triple t)
 {
     return(this._triples.Contains(t));
 }
 /// <summary>
 /// Adds a triple to the collection
 /// </summary>
 /// <param name="t">Triple</param>
 /// <returns></returns>
 protected internal override bool Add(Triple t)
 {
     return(this._triples.Add(t));
 }
Beispiel #5
0
 internal void AddRemovedTriple(Triple t)
 {
     _removedTriples.Add(t);
 }
Beispiel #6
0
 /// <summary>
 /// Returns whether the Store contains the given Triple within the Query Triples.
 /// </summary>
 /// <param name="t">Triple to search for.</param>
 /// <returns></returns>
 public bool Contains(Triple t)
 {
     return(_graphs.Any(g => g.ContainsTriple(t)));
 }
 /// <summary>
 /// Adds a Triple to the base collection
 /// </summary>
 /// <param name="t">Triple to add</param>
 protected internal override bool Add(Triple t)
 {
     return(this._baseCollection.Add(t));
 }
Beispiel #8
0
 /// <summary>
 /// Indexes a Triple.
 /// </summary>
 /// <param name="t">Triple.</param>
 private void Index(Triple t)
 {
     Index(t.Subject, t, _s, _sHash, _sComparer);
     Index(t.Predicate, t, _p, _pHash, _pComparer);
     Index(t.Object, t, _o, _oHash, _oComparer);
 }
Beispiel #9
0
        /// <summary>
        /// Uses a series of Rules to attempt to generate a mapping without the need for brute force guessing.
        /// </summary>
        /// <param name="subgraph">1st Graph.</param>
        /// <param name="parent">2nd Graph.</param>
        /// <param name="subNodes">1st Graph Node classification.</param>
        /// <param name="parentNodes">2nd Graph Node classification.</param>
        /// <param name="subDegrees">1st Graph Degree classification.</param>
        /// <param name="parentDegrees">2nd Graph Degree classification.</param>
        /// <returns></returns>
        private bool TryRulesBasedMapping(IGraph subgraph, IGraph parent, Dictionary <INode, int> subNodes, Dictionary <INode, int> parentNodes, Dictionary <int, int> subDegrees, Dictionary <int, int> parentDegrees)
        {
            // Start with new lists and dictionaries each time in case we get reused
            _unbound    = new List <INode>();
            _bound      = new List <INode>();
            _mapping    = new Dictionary <INode, INode>();
            _subTriples = new List <Triple>();

            // Initialise the Source Triples list
            _subTriples.AddRange(from t in subgraph.Triples
                                 where !t.IsGroundTriple
                                 select t);

            // First thing consider the trivial mapping
            Dictionary <INode, INode> trivialMapping = new Dictionary <INode, INode>();

            foreach (INode n in subNodes.Keys)
            {
                trivialMapping.Add(n, n);
            }
            List <Triple> targets = new List <Triple>(_parentTriples);

            if (_subTriples.All(t => targets.Remove(t.MapTriple(parent, trivialMapping))))
            {
                _mapping = trivialMapping;
                return(true);
            }

            // Initialise the Unbound list
            _unbound = (from n in parentNodes.Keys
                        select n).ToList();

            // Map single use Nodes first to reduce the size of the overall mapping
            foreach (KeyValuePair <INode, int> pair in subNodes.Where(p => p.Value == 1))
            {
                // Find the Triple we need to map
                Triple toMap = (from t in _subTriples
                                where t.Involves(pair.Key)
                                select t).First();

                foreach (INode n in _unbound.Where(n => parentNodes[n] == pair.Value))
                {
                    // See if this Mapping works
                    _mapping.Add(pair.Key, n);
                    if (_parentTriples.Remove(toMap.MapTriple(parent, _mapping)))
                    {
                        _subTriples.Remove(toMap);
                        _bound.Add(n);
                        break;
                    }
                    _mapping.Remove(pair.Key);
                }

                // If we couldn't map a single use Node then it's not a sub-graph
                if (!_mapping.ContainsKey(pair.Key))
                {
                    return(false);
                }
                else
                {
                    // Otherwise we can mark that Node as Bound
                    _unbound.Remove(_mapping[pair.Key]);
                }
            }

            // If all the Nodes were used only once and we mapped them all then it's a sub-graph
            if (_parentTriples.Count == 0)
            {
                return(true);
            }

            // Map any Nodes of unique degree next
            foreach (KeyValuePair <int, int> degreeClass in subDegrees)
            {
                if (degreeClass.Key > 1 && degreeClass.Value == 1)
                {
                    // There is a Node of degree greater than 1 than has a unique degree
                    // i.e. there is only one Node with this degree so there can only ever be one
                    // possible mapping for this Node
                    INode x = subNodes.FirstOrDefault(p => p.Value == degreeClass.Key).Key;
                    INode y = parentNodes.FirstOrDefault(p => p.Value == degreeClass.Key).Key;

                    // If either of these return null then the Graphs can't be equal
                    if (x == null || y == null)
                    {
                        return(false);
                    }

                    // Add the Mapping
                    _mapping.Add(x, y);
                    _bound.Add(y);
                    _unbound.Remove(y);
                }
            }

            // Work out which Nodes are paired up
            // By this we mean any Nodes which appear with other Nodes in a Triple
            // If multiple nodes appear together we can use this information to restrict
            // the possible mappings we generate
            List <MappingPair> subDependencies = new List <MappingPair>();

            foreach (Triple t in _subTriples)
            {
                if (t.Subject.NodeType == NodeType.Blank && t.Predicate.NodeType == NodeType.Blank && t.Object.NodeType == NodeType.Blank)
                {
                    throw new RdfException("GraphMatcher cannot compute mappings where a Triple is entirely composed of Blank Nodes");
                }
                if (t.Subject.NodeType == NodeType.Blank && t.Predicate.NodeType == NodeType.Blank)
                {
                    if (!t.Subject.Equals(t.Predicate))
                    {
                        subDependencies.Add(new MappingPair(t.Subject, t.Predicate, TripleIndexType.SubjectPredicate));
                    }
                }
                else if (t.Subject.NodeType == NodeType.Blank && t.Object.NodeType == NodeType.Blank)
                {
                    if (!t.Subject.Equals(t.Object))
                    {
                        subDependencies.Add(new MappingPair(t.Subject, t.Object, TripleIndexType.SubjectObject));
                    }
                }
                else if (t.Predicate.NodeType == NodeType.Blank && t.Object.NodeType == NodeType.Blank)
                {
                    if (!t.Predicate.Equals(t.Object))
                    {
                        subDependencies.Add(new MappingPair(t.Predicate, t.Object, TripleIndexType.PredicateObject));
                    }
                }
            }
            subDependencies = subDependencies.Distinct().ToList();
            List <MappingPair> parentDependencies = new List <MappingPair>();

            foreach (Triple t in _parentTriples)
            {
                if (t.Subject.NodeType == NodeType.Blank && t.Predicate.NodeType == NodeType.Blank && t.Object.NodeType == NodeType.Blank)
                {
                    throw new RdfException("GraphMatcher cannot compute mappings where a Triple is entirely composed of Blank Nodes");
                }
                if (t.Subject.NodeType == NodeType.Blank && t.Predicate.NodeType == NodeType.Blank)
                {
                    if (!t.Subject.Equals(t.Predicate))
                    {
                        parentDependencies.Add(new MappingPair(t.Subject, t.Predicate, TripleIndexType.SubjectPredicate));
                    }
                }
                else if (t.Subject.NodeType == NodeType.Blank && t.Object.NodeType == NodeType.Blank)
                {
                    if (!t.Subject.Equals(t.Object))
                    {
                        parentDependencies.Add(new MappingPair(t.Subject, t.Object, TripleIndexType.SubjectObject));
                    }
                }
                else if (t.Predicate.NodeType == NodeType.Blank && t.Object.NodeType == NodeType.Blank)
                {
                    if (!t.Predicate.Equals(t.Object))
                    {
                        parentDependencies.Add(new MappingPair(t.Predicate, t.Object, TripleIndexType.PredicateObject));
                    }
                }
            }
            parentDependencies = parentDependencies.Distinct().ToList();

            // Once we know of dependencies we can then map independent nodes
            List <INode> subIndependents = (from n in subNodes.Keys
                                            where !subDependencies.Any(p => p.Contains(n))
                                            select n).ToList();
            List <INode> parentIndependents = (from n in parentNodes.Keys
                                               where !parentDependencies.Any(p => p.Contains(n))
                                               select n).ToList();

            // If the number of independent nodes in the sub-graph is greater than it cannot be a sub-graph
            if (subIndependents.Count > parentIndependents.Count)
            {
                return(false);
            }

            // Try to map the independent nodes
            foreach (INode x in subIndependents)
            {
                // They may already be mapped as they may be single use Triples
                if (_mapping.ContainsKey(x))
                {
                    continue;
                }

                List <Triple> xs = _subTriples.Where(t => t.Involves(x)).ToList();
                foreach (INode y in parentIndependents)
                {
                    if (subNodes[x] != parentNodes[y])
                    {
                        continue;
                    }

                    _mapping.Add(x, y);

                    // Test the mapping
                    List <Triple> ys = _parentTriples.Where(t => t.Involves(y)).ToList();
                    if (xs.All(t => ys.Remove(t.MapTriple(parent, _mapping))))
                    {
                        // This is a valid mapping
                        xs.ForEach(t => _parentTriples.Remove(t.MapTriple(parent, _mapping)));
                        xs.ForEach(t => _subTriples.Remove(t));
                        break;
                    }
                    _mapping.Remove(x);
                }

                // If we couldn't map an independent Node then we fail
                if (!_mapping.ContainsKey(x))
                {
                    return(false);
                }
            }

            // Want to save our mapping so far here as if the mapping we produce using the dependency information
            // is flawed then we'll have to attempt brute force
            Dictionary <INode, INode> baseMapping = new Dictionary <INode, INode>(_mapping);

            // Now we use the dependency information to try and find mappings
            foreach (MappingPair dependency in subDependencies)
            {
                // If both dependent Nodes are already mapped we don't need to try mapping them again
                if (_mapping.ContainsKey(dependency.X) && _mapping.ContainsKey(dependency.Y))
                {
                    continue;
                }

                // Get all the Triples with this Pair in them
                List <Triple> xs;
                bool          canonical = false;
                switch (dependency.Type)
                {
                case TripleIndexType.SubjectPredicate:
                    xs = (from t in _subTriples
                          where t.Subject.Equals(dependency.X) && t.Predicate.Equals(dependency.Y)
                          select t).ToList();
                    if (xs.Count == 1)
                    {
                        canonical = ((from t in _subTriples
                                      where t.Subject.NodeType == NodeType.Blank && t.Predicate.NodeType == NodeType.Blank && t.Object.Equals(xs[0].Object)
                                      select t).Count() == 1);
                    }
                    break;

                case TripleIndexType.SubjectObject:
                    xs = (from t in _subTriples
                          where t.Subject.Equals(dependency.X) && t.Object.Equals(dependency.Y)
                          select t).ToList();
                    if (xs.Count == 1)
                    {
                        canonical = ((from t in _subTriples
                                      where t.Subject.NodeType == NodeType.Blank && t.Predicate.Equals(xs[0].Predicate) && t.Object.NodeType == NodeType.Blank
                                      select t).Count() == 1);
                    }
                    break;

                case TripleIndexType.PredicateObject:
                    xs = (from t in _subTriples
                          where t.Predicate.Equals(dependency.X) && t.Object.Equals(dependency.Y)
                          select t).ToList();
                    if (xs.Count == 1)
                    {
                        canonical = ((from t in _subTriples
                                      where t.Subject.Equals(xs[0].Subject) && t.Predicate.NodeType == NodeType.Blank && t.Object.NodeType == NodeType.Blank
                                      select t).Count() == 1);
                    }
                    break;

                default:
                    // This means we've gone wrong somehow
                    throw new RdfException("Unknown exception occurred while trying to generate a Mapping between the two Graphs");
                }

                bool xbound = _mapping.ContainsKey(dependency.X);
                bool ybound = _mapping.ContainsKey(dependency.Y);

                // Look at all the possible Target Dependencies we could map to
                foreach (MappingPair target in parentDependencies)
                {
                    if (target.Type != dependency.Type)
                    {
                        continue;
                    }

                    // If one of the Nodes we're trying to map was already mapped then we can further restrict
                    // candidate mappings
                    if (xbound)
                    {
                        if (!target.X.Equals(_mapping[dependency.X]))
                        {
                            continue;
                        }
                    }
                    if (ybound)
                    {
                        if (!target.Y.Equals(_mapping[dependency.Y]))
                        {
                            continue;
                        }
                    }

                    // If the Nodes in the Target have already been used then we can discard this possible mapping
                    if (!xbound && _mapping.ContainsValue(target.X))
                    {
                        continue;
                    }
                    if (!ybound && _mapping.ContainsValue(target.Y))
                    {
                        continue;
                    }

                    // Get the Triples with the Target Pair in them
                    List <Triple> ys;
                    switch (target.Type)
                    {
                    case TripleIndexType.SubjectPredicate:
                        ys = (from t in _parentTriples
                              where t.Subject.Equals(target.X) && t.Predicate.Equals(target.Y)
                              select t).ToList();
                        break;

                    case TripleIndexType.SubjectObject:
                        ys = (from t in _parentTriples
                              where t.Subject.Equals(target.X) && t.Object.Equals(target.Y)
                              select t).ToList();
                        break;

                    case TripleIndexType.PredicateObject:
                        ys = (from t in _parentTriples
                              where t.Predicate.Equals(target.X) && t.Object.Equals(target.Y)
                              select t).ToList();
                        break;

                    default:
                        // This means we've gone wrong somehow
                        throw new RdfException("Unknown exception occurred while trying to generate a Mapping between the two Graphs");
                    }

                    // If the pairs are involved in a greater number of Triples in the sub-graph it cannot be a valid mapping
                    if (xs.Count > ys.Count)
                    {
                        continue;
                    }

                    // If all the Triples in xs can be removed from ys then this is a valid mapping
                    if (!xbound)
                    {
                        _mapping.Add(dependency.X, target.X);
                    }
                    if (!ybound)
                    {
                        _mapping.Add(dependency.Y, target.Y);
                    }
                    if (xs.All(t => ys.Remove(t.MapTriple(parent, _mapping))))
                    {
                        if (canonical)
                        {
                            // If this was the only possible mapping for this Pair then this is a canonical mapping
                            // and can go in the base mapping so if we have to brute force we have fewer possibles
                            // to try
                            if (!baseMapping.ContainsKey(dependency.X))
                            {
                                baseMapping.Add(dependency.X, target.X);
                            }
                            if (!baseMapping.ContainsKey(dependency.Y))
                            {
                                baseMapping.Add(dependency.Y, target.Y);
                            }
                        }
                        _bound.Add(target.X);
                        _bound.Add(target.Y);
                        _unbound.Remove(target.X);
                        _unbound.Remove(target.Y);
                        break;
                    }
                    else
                    {
                        if (!xbound)
                        {
                            _mapping.Remove(dependency.X);
                        }
                        if (!ybound)
                        {
                            _mapping.Remove(dependency.Y);
                        }
                    }
                }
            }

            // If we've filled in the Mapping fully then the Graph is hopefully a sub-graph of the parent graph
            if (_mapping.Count == subNodes.Count)
            {
                // Need to check we found a valid mapping
                List <Triple> ys = new List <Triple>(_parentTriples);
                if (_subTriples.All(t => ys.Remove(t.MapTriple(parent, _mapping))))
                {
                    return(true);
                }
                else
                {
                    _mapping = baseMapping;
                    return(TryBruteForceMapping(subgraph, parent, subNodes, parentNodes, subDependencies, parentDependencies));
                }
            }
            else
            {
                return(TryBruteForceMapping(subgraph, parent, subNodes, parentNodes, subDependencies, parentDependencies));
            }
        }
 /// <summary>
 /// Compares two Triples
 /// </summary>
 /// <param name="x">Triple</param>
 /// <param name="y">Triple</param>
 /// <returns></returns>
 public override int Compare(Triple x, Triple y)
 {
     return(_nodeComparer.Compare(x.Object, y.Object));
 }
 /// <summary>
 /// Compares two Triples
 /// </summary>
 /// <param name="x">Triple</param>
 /// <param name="y">Triple</param>
 /// <returns></returns>
 public override int Compare(Triple x, Triple y)
 {
     return(_nodeComparer.Compare(x.Predicate, y.Predicate));
 }
Beispiel #12
0
 /// <summary>
 /// Gets whether a given Triple exists in this Graph.
 /// </summary>
 /// <param name="t">Triple to test.</param>
 /// <returns></returns>
 public virtual bool ContainsTriple(Triple t)
 {
     return(_g.ContainsTriple(t));
 }
Beispiel #13
0
 /// <summary>
 /// Retracts a Triple from the Graph.
 /// </summary>
 /// <param name="t">Triple.</param>
 public virtual bool Retract(Triple t)
 {
     return(_g.Retract(t));
 }
Beispiel #14
0
 /// <summary>
 /// Asserts a Triple in the Graph.
 /// </summary>
 /// <param name="t">Triple.</param>
 public virtual bool Assert(Triple t)
 {
     return(_g.Assert(t.CopyTriple(_g)));
 }
Beispiel #15
0
 /// <summary>
 /// Unindexes a triple.
 /// </summary>
 /// <param name="t">Triple.</param>
 private void Unindex(Triple t)
 {
     Unindex(t.Subject, t, _s);
     Unindex(t.Predicate, t, _p);
     Unindex(t.Object, t, _o);
 }
Beispiel #16
0
 /// <summary>
 /// Checks whether the collection contains a given Triple.
 /// </summary>
 /// <param name="t">Triple.</param>
 /// <returns></returns>
 public override bool Contains(Triple t)
 {
     return(_triples.ContainsKey(t));
 }
Beispiel #17
0
 /// <summary>
 /// Copies a Triple from one Graph to another
 /// </summary>
 /// <param name="t">Triple to copy</param>
 /// <param name="target">Graph to copy to</param>
 /// <returns></returns>
 public static Triple CopyTriple(Triple t, IGraph target)
 {
     return(CopyTriple(t, target, false));
 }
 /// <summary>
 /// Deletes a Triple from the base collection
 /// </summary>
 /// <param name="t">Triple to delete</param>
 protected internal override bool Delete(Triple t)
 {
     return(this._baseCollection.Delete(t));
 }
Beispiel #19
0
 /// <summary>
 /// Creates a new set of Triple Event Arguments for the given Triple
 /// </summary>
 /// <param name="t">Triple</param>
 /// <param name="g">Graph the Triple Event occurred in</param>
 public TripleEventArgs(Triple t, IGraph g)
     : base()
 {
     this._t = t;
     this._g = g;
 }
 /// <summary>
 /// Checks whether the union contains this Triple in any of the collections it comprises
 /// </summary>
 /// <param name="t">Triple to test</param>
 /// <returns></returns>
 public override bool Contains(Triple t)
 {
     return(this._collections.Any(c => c.Contains(t)));
 }
Beispiel #21
0
 /// <summary>
 /// Creates a new set of Triple Event Arguments for the given Triple
 /// </summary>
 /// <param name="t">Triple</param>
 /// <param name="g">Graph the Triple Event occurred in</param>
 /// <param name="asserted">Was the Triple Asserted (if not then it was Retracted)</param>
 public TripleEventArgs(Triple t, IGraph g, bool asserted)
     : this(t, g)
 {
     this._added = asserted;
 }
 /// <summary>
 /// Deletes a triple from the collection
 /// </summary>
 /// <param name="t">Triple</param>
 /// <returns></returns>
 protected internal override bool Delete(Triple t)
 {
     return(this._triples.Delete(t));
 }
Beispiel #23
0
 internal void AddAddedTriple(Triple t)
 {
     _addedTriples.Add(t);
 }