Neuron®
The Neuron® is the basis for the creation of open and secure federated networks for smart societies.
Loading...
Searching...
No Matches
SparqlRegularPattern.cs
2using System.Threading.Tasks;
8
10{
15 {
16 private ChunkedList<SemanticQueryTriple> triples = null;
17 private ChunkedList<KeyValuePair<ScriptNode, ScriptNode>> boundVariables = null;
18 private ChunkedList<IFilterNode> filter = null;
19
24 {
25 }
26
30 public bool IsEmpty => !(this.HasTriples || this.HasBoundVariables || this.HasFilter);
31
36
40 public int TripleCount => this.triples?.Count ?? 0;
41
45 public IEnumerable<KeyValuePair<ScriptNode, ScriptNode>> BoundVariables => this.boundVariables;
46
50 public IEnumerable<IFilterNode> Filter => this.filter;
51
55 public bool HasTriples => !(this.triples is null);
56
60 public bool HasBoundVariables => !(this.boundVariables is null);
61
65 public bool HasFilter => !(this.filter is null);
66
71 public void AddTriple(SemanticQueryTriple Triple)
72 {
73 if (this.triples is null)
74 this.triples = new ChunkedList<SemanticQueryTriple>();
75
76 this.triples.Add(Triple);
77 }
78
85 {
86 if (this.boundVariables is null)
87 this.boundVariables = new ChunkedList<KeyValuePair<ScriptNode, ScriptNode>>();
88
89 this.boundVariables.Add(new KeyValuePair<ScriptNode, ScriptNode>(Value, Variable));
90 }
91
97 {
98 if (this.filter is null)
99 this.filter = new ChunkedList<IFilterNode>();
100
101 if (Filter is IFilterNode FilterNode)
102 this.filter.Add(FilterNode);
103 else
104 this.filter.Add(new FilterScriptNode(Filter));
105 }
106
114 public Task<IEnumerable<Possibility>> Search(ISemanticCube Cube, Variables Variables,
115 SparqlQuery Query)
116 {
117 return this.Search(Cube, Variables, null, Query);
118 }
119
128 public async Task<IEnumerable<Possibility>> Search(ISemanticCube Cube,
129 Variables Variables, IEnumerable<Possibility> ExistingMatches,
130 SparqlQuery Query)
131 {
132 if (this.HasTriples)
133 {
134 foreach (SemanticQueryTriple T in this.triples)
135 {
136 switch (T.Type)
137 {
138 case QueryTripleType.Constant:
140 return null;
141 break;
142
143 case QueryTripleType.SubjectVariable:
144 ExistingMatches = await this.CrossPossibilitiesOneVariable(ExistingMatches, T, 0, 1, 2, Cube);
145 break;
146
147 case QueryTripleType.PredicateVariable:
148 ExistingMatches = await this.CrossPossibilitiesOneVariable(ExistingMatches, T, 1, 0, 2, Cube);
149 break;
150
151 case QueryTripleType.ObjectVariable:
152 ExistingMatches = await this.CrossPossibilitiesOneVariable(ExistingMatches, T, 2, 0, 1, Cube);
153 break;
154
155 case QueryTripleType.SubjectPredicateVariables:
156 ExistingMatches = await this.CrossPossibilitiesTwoVariables(ExistingMatches, T, 0, 1, 2, Cube);
157 break;
158
159 case QueryTripleType.SubjectObjectVariable:
160 ExistingMatches = await this.CrossPossibilitiesTwoVariables(ExistingMatches, T, 0, 2, 1, Cube);
161 break;
162
163 case QueryTripleType.PredicateObjectVariable:
164 ExistingMatches = await this.CrossPossibilitiesTwoVariables(ExistingMatches, T, 1, 2, 0, Cube);
165 break;
166
167 case QueryTripleType.SubjectPredicateObjectVariable:
168 ExistingMatches = await this.CrossPossibilitiesThreeVariables(ExistingMatches, T, Cube);
169 break;
170 }
171
172 if (ExistingMatches is null)
173 return null;
174
175 using (IEnumerator<Possibility> e = ExistingMatches.GetEnumerator())
176 {
177 if (!e.MoveNext())
178 return null;
179 }
180 }
181 }
182
183 if (this.HasBoundVariables && !(ExistingMatches is null))
184 {
186 ObjectProperties RecordVariables = null;
187 Possibility P;
188 string Name;
189
190 foreach (Possibility Possibility in ExistingMatches)
191 {
192 P = Possibility;
193
194 foreach (KeyValuePair<ScriptNode, ScriptNode> P2 in this.boundVariables)
195 {
196 if (RecordVariables is null)
197 RecordVariables = new ObjectProperties(P, Variables);
198 else
199 RecordVariables.Object = P;
200
201 if (P2.Value is VariableReference Ref)
202 Name = Ref.VariableName;
203 else
204 {
205 object Obj = await SparqlQuery.EvaluateValue(RecordVariables, P2.Value);
206 if (Obj is null)
207 continue;
208
209 Name = Obj.ToString();
210 if (string.IsNullOrEmpty(Name))
211 continue;
212 }
213
214 ISemanticElement Literal = await Query.EvaluateSemanticElement(RecordVariables, P2.Key);
215 if (!(Literal is null))
216 P = new Possibility(Name, Literal, P);
217 }
218
219 NewMatches.Add(P);
220 }
221
222 ExistingMatches = NewMatches;
223 }
224
225 if (this.HasFilter && !(ExistingMatches is null))
226 {
227 ChunkedList<Possibility> Filtered = null;
228 ObjectProperties RecordVariables = null;
229 bool Pass;
230
231 foreach (Possibility P in ExistingMatches)
232 {
233 if (RecordVariables is null)
234 RecordVariables = new ObjectProperties(P, Variables);
235 else
236 RecordVariables.Object = P;
237
238 Pass = true;
239
240 foreach (IFilterNode Filter in this.filter)
241 {
242 object Value = await SparqlQuery.EvaluateValue(RecordVariables, Filter, Cube, Query, P);
243 if (!(Value is bool b) || !b)
244 {
245 Pass = false;
246 break;
247 }
248 }
249
250 if (Pass)
251 {
252 if (Filtered is null)
253 Filtered = new ChunkedList<Possibility>();
254
255 Filtered.Add(P);
256 }
257 }
258
259 ExistingMatches = Filtered;
260 }
261
262 return ExistingMatches;
263 }
264
265 private async Task<IEnumerable<Possibility>> CrossPossibilitiesOneVariable(
266 IEnumerable<Possibility> Possibilities, SemanticQueryTriple T, int VariableIndex,
267 int ValueIndex1, int ValueIndex2, ISemanticCube Cube)
268 {
269 ChunkedList<Possibility> NewPossibilities = null;
270 string Name = T.VariableName(VariableIndex);
271 ISemanticElement Value;
272
273 if (Possibilities is null)
274 {
275 IEnumerable<ISemanticTriple> NewTriples = await Cube.GetTriples(
276 T[ValueIndex1], ValueIndex1, T[ValueIndex2], ValueIndex2);
277
278 if (NewTriples is null)
279 return null;
280
281 NewPossibilities = new ChunkedList<Possibility>();
282
283 foreach (ISemanticTriple T2 in NewTriples)
284 NewPossibilities.Add(new Possibility(Name, T2[VariableIndex]));
285 }
286 else
287 {
288 foreach (Possibility P in Possibilities)
289 {
290 Value = P.GetValue(Name);
291 if (Value is null)
292 {
293 IEnumerable<ISemanticTriple> NewTriples = await Cube.GetTriples(
294 T[ValueIndex1], ValueIndex1, T[ValueIndex2], ValueIndex2);
295
296 if (NewTriples is null)
297 continue;
298
299 if (NewPossibilities is null)
300 NewPossibilities = new ChunkedList<Possibility>();
301
302 foreach (ISemanticTriple T2 in NewTriples)
303 NewPossibilities.Add(new Possibility(Name, T2[VariableIndex], P));
304 }
305 else
306 {
307 if (await Cube.GetTriplesBySubjectAndPredicateAndObject(Value, T.Predicate, T.Object) is null)
308 continue;
309
310 if (NewPossibilities is null)
311 NewPossibilities = new ChunkedList<Possibility>();
312
313 NewPossibilities.Add(P);
314 }
315 }
316 }
317
318 return NewPossibilities;
319 }
320
321 private async Task<IEnumerable<Possibility>> CrossPossibilitiesTwoVariables(
322 IEnumerable<Possibility> Possibilities, SemanticQueryTriple T, int VariableIndex1,
323 int VariableIndex2, int ValueIndex, ISemanticCube Cube)
324 {
325 ChunkedList<Possibility> NewPossibilities = null;
326 string Name = T.VariableName(VariableIndex1);
327 string Name2 = T.VariableName(VariableIndex2);
328 ISemanticElement Value;
329 ISemanticElement Value2;
330 bool SameName = Name == Name2;
331
332 if (Possibilities is null)
333 {
334 IEnumerable<ISemanticTriple> Triples = await Cube.GetTriples(T[ValueIndex], ValueIndex);
335 if (Triples is null)
336 return null;
337
338 foreach (ISemanticTriple T2 in Triples)
339 {
340 if (SameName)
341 {
342 ISemanticElement E = T2[VariableIndex1];
343
344 if (!E.Equals(T2[VariableIndex2]))
345 continue;
346
347 if (NewPossibilities is null)
348 NewPossibilities = new ChunkedList<Possibility>();
349
350 NewPossibilities.Add(new Possibility(Name, E));
351 }
352 else
353 {
354 if (NewPossibilities is null)
355 NewPossibilities = new ChunkedList<Possibility>();
356
357 NewPossibilities.Add(
358 new Possibility(Name, T2[VariableIndex1],
359 new Possibility(Name2, T2[VariableIndex2])));
360 }
361 }
362 }
363 else
364 {
365 foreach (Possibility P in Possibilities)
366 {
367 Value = P.GetValue(Name);
368
369 if (SameName)
370 Value2 = Value;
371 else
372 Value2 = P.GetValue(Name2);
373
374 bool IsProcessed = !(Value is null);
375 bool IsProcessed2 = !(Value2 is null);
376
377 if (IsProcessed && IsProcessed2)
378 {
379 if (await Cube.GetTriplesBySubjectAndPredicateAndObject(Value, Value2, T[ValueIndex]) is null)
380 continue;
381
382 if (NewPossibilities is null)
383 NewPossibilities = new ChunkedList<Possibility>();
384
385 NewPossibilities.Add(P);
386 }
387 else if (IsProcessed)
388 {
389 this.CrossPossibilities(
390 await Cube.GetTriples(Value, VariableIndex1, T[ValueIndex], ValueIndex),
391 P, Name2, VariableIndex2, ref NewPossibilities);
392 }
393 else if (IsProcessed2)
394 {
395 this.CrossPossibilities(
396 await Cube.GetTriples(Value2, VariableIndex2, T[ValueIndex], ValueIndex),
397 P, Name, VariableIndex1, ref NewPossibilities);
398 }
399 else
400 {
401 IEnumerable<ISemanticTriple> Triples = await Cube.GetTriples(T[ValueIndex], ValueIndex);
402 if (Triples is null)
403 return null;
404
405 foreach (ISemanticTriple T2 in Triples)
406 {
407 if (SameName)
408 {
409 ISemanticElement E = T2[VariableIndex1];
410
411 if (!E.Equals(T2[VariableIndex2]))
412 continue;
413
414 if (NewPossibilities is null)
415 NewPossibilities = new ChunkedList<Possibility>();
416
417 NewPossibilities.Add(new Possibility(Name, E, P));
418 }
419 else
420 {
421 if (NewPossibilities is null)
422 NewPossibilities = new ChunkedList<Possibility>();
423
424 NewPossibilities.Add(
425 new Possibility(Name, T2[VariableIndex1],
426 new Possibility(Name2, T2[VariableIndex2], P)));
427 }
428 }
429 }
430
431 }
432 }
433
434 return NewPossibilities;
435 }
436
437 private async Task<IEnumerable<Possibility>> CrossPossibilitiesThreeVariables(
438 IEnumerable<Possibility> Possibilities, SemanticQueryTriple T, ISemanticCube Cube)
439 {
440 ChunkedList<Possibility> NewPossibilities = null;
441 string Name = T.SubjectVariable;
442 string Name2 = T.PredicateVariable;
443 string Name3 = T.ObjectVariable;
444 bool SameName = Name == Name2;
445 bool SameName2 = Name == Name3;
446 bool SameName3 = Name2 == Name3;
447
448 if (Possibilities is null)
449 {
450 foreach (ISemanticTriple T2 in Cube)
451 {
452 if (SameName && !T2.Subject.Equals(T2.Predicate))
453 continue;
454
455 if (SameName2 && !T2.Subject.Equals(T2.Object))
456 continue;
457
458 if (SameName3 && !T2.Predicate.Equals(T2.Object))
459 continue;
460
461 Possibility NewPossibility = new Possibility(Name, T2.Subject);
462
463 if (!SameName)
464 NewPossibility = new Possibility(Name2, T2.Predicate, NewPossibility);
465
466 if (!SameName2 && !SameName3)
467 NewPossibility = new Possibility(Name3, T2.Object, NewPossibility);
468
469 if (NewPossibilities is null)
470 NewPossibilities = new ChunkedList<Possibility>();
471
472 NewPossibilities.Add(NewPossibility);
473 }
474 }
475 else
476 {
477 foreach (Possibility P in Possibilities)
478 {
479 ISemanticElement Value = P.GetValue(Name);
480 ISemanticElement Value2 = SameName ? Value : P.GetValue(Name2);
481 ISemanticElement Value3 = SameName2 ? Value : SameName3 ? Value2 : P.GetValue(Name3);
482 bool IsProcessed = !(Value is null);
483 bool IsProcessed2 = !(Value2 is null);
484 bool IsProcessed3 = !(Value3 is null);
485
486 if (IsProcessed && IsProcessed2 && IsProcessed3)
487 {
488 if (await Cube.GetTriplesBySubjectAndPredicateAndObject(Value, Value2, Value3) is null)
489 continue;
490
491 if (NewPossibilities is null)
492 NewPossibilities = new ChunkedList<Possibility>();
493
494 NewPossibilities.Add(P);
495 }
496 else if (IsProcessed && IsProcessed2) // Subject & Predicate variables already processed
497 {
498 this.CrossPossibilities(
499 await Cube.GetTriplesBySubjectAndPredicate(Value, Value2),
500 P, Name3, 2, ref NewPossibilities);
501 }
502 else if (IsProcessed && IsProcessed3) // Subject & Object variables already processed
503 {
504 this.CrossPossibilities(
505 await Cube.GetTriplesBySubjectAndObject(Value, Value3),
506 P, Name2, 1, ref NewPossibilities);
507 }
508 else if (IsProcessed2 && IsProcessed3) // Predicate & Object variables already processed
509 {
510 this.CrossPossibilities(
511 await Cube.GetTriplesByPredicateAndObject(Value2, Value3),
512 P, Name, 0, ref NewPossibilities);
513 }
514 else if (IsProcessed) // Subject variable processed
515 {
516 ISemanticPlane Plane = await Cube.GetTriplesBySubject(Value);
517 if (Plane is null)
518 continue;
519
520 foreach (ISemanticTriple T2 in Plane)
521 {
522 if (SameName3)
523 {
524 if (!T2.Predicate.Equals(T2.Object))
525 continue;
526
527 if (NewPossibilities is null)
528 NewPossibilities = new ChunkedList<Possibility>();
529
530 NewPossibilities.Add(new Possibility(Name2, T2.Predicate, P));
531 }
532 else
533 {
534 if (NewPossibilities is null)
535 NewPossibilities = new ChunkedList<Possibility>();
536
537 NewPossibilities.Add(
538 new Possibility(Name2, T2.Predicate,
539 new Possibility(Name3, T2.Object, P)));
540 }
541 }
542 }
543 else if (IsProcessed2) // Predicate variable processed
544 {
545 ISemanticPlane Plane = await Cube.GetTriplesByPredicate(Value2);
546 if (Plane is null)
547 continue;
548
549 foreach (ISemanticTriple T2 in Plane)
550 {
551 if (SameName2)
552 {
553 if (!T2.Subject.Equals(T2.Object))
554 continue;
555
556 if (NewPossibilities is null)
557 NewPossibilities = new ChunkedList<Possibility>();
558
559 NewPossibilities.Add(new Possibility(Name, T2.Subject, P));
560 }
561 else
562 {
563 if (NewPossibilities is null)
564 NewPossibilities = new ChunkedList<Possibility>();
565
566 NewPossibilities.Add(
567 new Possibility(Name, T2.Subject,
568 new Possibility(Name3, T2.Object, P)));
569 }
570 }
571 }
572 else if (IsProcessed3) // Object variable processed
573 {
574 ISemanticPlane Plane = await Cube.GetTriplesByObject(Value3);
575 if (Plane is null)
576 continue;
577
578 foreach (ISemanticTriple T2 in Plane)
579 {
580 if (SameName)
581 {
582 if (!T2.Subject.Equals(T2.Predicate))
583 continue;
584
585 if (NewPossibilities is null)
586 NewPossibilities = new ChunkedList<Possibility>();
587
588 NewPossibilities.Add(new Possibility(Name, T2.Subject, P));
589 }
590 else
591 {
592 if (NewPossibilities is null)
593 NewPossibilities = new ChunkedList<Possibility>();
594
595 NewPossibilities.Add(
596 new Possibility(Name, T2.Subject,
597 new Possibility(Name2, T2.Predicate, P)));
598 }
599 }
600 }
601 else
602 {
603 foreach (ISemanticTriple T2 in Cube)
604 {
605 if (SameName && !T2.Subject.Equals(T2.Predicate))
606 continue;
607
608 if (SameName2 && !T2.Subject.Equals(T2.Object))
609 continue;
610
611 if (SameName3 && !T2.Predicate.Equals(T2.Object))
612 continue;
613
614 Possibility NewPossibility = new Possibility(Name, T2.Subject, P);
615
616 if (!SameName)
617 NewPossibility = new Possibility(Name2, T2.Predicate, NewPossibility);
618
619 if (!SameName2 && !SameName3)
620 NewPossibility = new Possibility(Name3, T2.Object, NewPossibility);
621
622 if (NewPossibilities is null)
623 NewPossibilities = new ChunkedList<Possibility>();
624
625 NewPossibilities.Add(NewPossibility);
626 }
627 }
628 }
629 }
630
631 return NewPossibilities;
632 }
633
634 private void CrossPossibilities(IEnumerable<ISemanticTriple> NewTriples,
635 Possibility Possibility, string Name, int Index, ref ChunkedList<Possibility> NewPossibilities)
636 {
637 if (NewTriples is null)
638 return;
639
640 if (NewPossibilities is null)
641 NewPossibilities = new ChunkedList<Possibility>();
642
643 foreach (ISemanticTriple T2 in NewTriples)
644 NewPossibilities.Add(new Possibility(Name, T2[Index], Possibility));
645 }
646
654 public bool ForAllChildNodes(ScriptNodeEventHandler Callback, object State, SearchMethod Order)
655 {
656 if (Order == SearchMethod.DepthFirst)
657 {
658 if (!(this.triples is null))
659 {
660 foreach (ISemanticTriple T in this.triples)
661 {
663 {
664 if (!S.Node.ForAllChildNodes(Callback, State, Order))
665 return false;
666 }
667
669 {
670 if (!P.Node.ForAllChildNodes(Callback, State, Order))
671 return false;
672 }
673
674 if (T.Object is SemanticScriptElement O)
675 {
676 if (!O.Node.ForAllChildNodes(Callback, State, Order))
677 return false;
678 }
679 }
680 }
681
682 if (!(this.boundVariables is null))
683 {
684 foreach (KeyValuePair<ScriptNode, ScriptNode> P in this.boundVariables)
685 {
686 if (!P.Key.ForAllChildNodes(Callback, State, Order))
687 return false;
688
689 if (!P.Value.ForAllChildNodes(Callback, State, Order))
690 return false;
691 }
692 }
693
694 if (!(this.filter is null))
695 {
696 foreach (IFilterNode P in this.filter)
697 {
698 if (!P.ScriptNode.ForAllChildNodes(Callback, State, Order))
699 return false;
700 }
701 }
702 }
703
704 this.ForAll(Callback, State, Order);
705
706 if (Order == SearchMethod.BreadthFirst)
707 {
708 if (!(this.triples is null))
709 {
710 foreach (ISemanticTriple T in this.triples)
711 {
713 {
714 if (!S.Node.ForAllChildNodes(Callback, State, Order))
715 return false;
716 }
717
719 {
720 if (!P.Node.ForAllChildNodes(Callback, State, Order))
721 return false;
722 }
723
724 if (T.Object is SemanticScriptElement O)
725 {
726 if (!O.Node.ForAllChildNodes(Callback, State, Order))
727 return false;
728 }
729 }
730 }
731
732 if (!(this.boundVariables is null))
733 {
734 foreach (KeyValuePair<ScriptNode, ScriptNode> P in this.boundVariables)
735 {
736 if (!P.Key.ForAllChildNodes(Callback, State, Order))
737 return false;
738
739 if (!P.Value.ForAllChildNodes(Callback, State, Order))
740 return false;
741 }
742 }
743
744 if (!(this.filter is null))
745 {
746 foreach (IFilterNode P in this.filter)
747 {
748 if (!P.ScriptNode.ForAllChildNodes(Callback, State, Order))
749 return false;
750 }
751 }
752 }
753
754 return true;
755 }
756
764 public bool ForAll(ScriptNodeEventHandler Callback, object State, SearchMethod Order)
765 {
766 int i, c;
767
768 if (!(this.triples is null))
769 {
770 ChunkNode<SemanticQueryTriple> Loop = this.triples.FirstChunk;
772
773 while (!(Loop is null))
774 {
775 for (i = Loop.Start, c = Loop.Pos; i < c; i++)
776 {
777 T = Loop[i];
778
780 {
781 if (!S.ForAll(Callback, State, Order))
782 return false;
783 }
784
786 {
787 if (!P.ForAll(Callback, State, Order))
788 return false;
789 }
790
791 if (T.Object is SemanticScriptElement O)
792 {
793 if (!O.ForAll(Callback, State, Order))
794 return false;
795 }
796 }
797
798 Loop = Loop.Next;
799 }
800 }
801
802 if (!(this.boundVariables is null))
803 {
805 KeyValuePair<ScriptNode, ScriptNode> P;
806
807 while (!(Loop is null))
808 {
809 for (i = Loop.Start, c = Loop.Pos; i < c; i++)
810 {
811 P = Loop[i];
812
813 if (!Callback(P.Key, out ScriptNode NewKey, State))
814 return false;
815
816 if (!Callback(P.Value, out ScriptNode NewValue, State))
817 return false;
818
819 if (!(NewKey is null) || !(NewValue is null))
820 {
821 Loop[i] = new KeyValuePair<ScriptNode, ScriptNode>(
822 NewKey ?? P.Key, NewValue ?? P.Value);
823 }
824 }
825
826 Loop = Loop.Next;
827 }
828 }
829
830 if (!(this.filter is null))
831 {
832 ChunkNode<IFilterNode> Loop = this.filter.FirstChunk;
833
834 while (!(Loop is null))
835 {
836 for (i = Loop.Start, c = Loop.Pos; i < c; i++)
837 {
838 if (!Callback(Loop[i].ScriptNode, out ScriptNode NewValue, State))
839 return false;
840
841 if (!(NewValue is null))
842 {
843 if (NewValue is IFilterNode NewFilterNode)
844 Loop[i] = NewFilterNode;
845 else
846 Loop[i] = new FilterScriptNode(NewValue);
847 }
848 }
849
850 Loop = Loop.Next;
851 }
852 }
853
854 return true;
855 }
856
858 public override bool Equals(object obj)
859 {
860 if (!(obj is SparqlRegularPattern Typed) ||
861 this.triples is null ^ Typed.triples is null ||
862 this.boundVariables is null ^ Typed.boundVariables is null ||
863 this.filter is null ^ Typed.filter is null)
864 {
865 return false;
866 }
867
868 if (!(this.boundVariables is null))
869 {
870 IEnumerator<KeyValuePair<ScriptNode, ScriptNode>> e1 = this.boundVariables.GetEnumerator();
871 IEnumerator<KeyValuePair<ScriptNode, ScriptNode>> e2 = Typed.boundVariables.GetEnumerator();
872
873 try
874 {
875 bool b1 = e1.MoveNext();
876 bool b2 = e2.MoveNext();
877
878 while (b1 && b2)
879 {
880 if (!e1.Current.Equals(e2.Current))
881 return false;
882
883 b1 = e1.MoveNext();
884 b2 = e2.MoveNext();
885 }
886
887 if (b1 || b2)
888 return false;
889 }
890 finally
891 {
892 e1.Dispose();
893 e2.Dispose();
894 }
895 }
896
897 if (!(this.filter is null))
898 {
899 IEnumerator<IFilterNode> e1 = this.filter.GetEnumerator();
900 IEnumerator<IFilterNode> e2 = Typed.filter.GetEnumerator();
901
902 try
903 {
904 bool b1 = e1.MoveNext();
905 bool b2 = e2.MoveNext();
906
907 while (b1 && b2)
908 {
909 if (!e1.Current.Equals(e2.Current))
910 return false;
911
912 b1 = e1.MoveNext();
913 b2 = e2.MoveNext();
914 }
915
916 if (b1 || b2)
917 return false;
918 }
919 finally
920 {
921 e1.Dispose();
922 e2.Dispose();
923 }
924 }
925
926 return true;
927 }
928
930 public override int GetHashCode()
931 {
932 int Result = base.GetHashCode();
933
934 if (!(this.triples is null))
935 {
936 foreach (SemanticQueryTriple T in this.triples)
937 Result ^= Result << 5 ^ T.GetHashCode();
938 }
939
940 if (!(this.boundVariables is null))
941 {
942 foreach (KeyValuePair<ScriptNode, ScriptNode> P in this.boundVariables)
943 {
944 Result ^= Result << 5 ^ P.Key.GetHashCode();
945 Result ^= Result << 5 ^ P.Value.GetHashCode();
946 }
947 }
948
949 if (!(this.filter is null))
950 {
951 foreach (IFilterNode N in this.filter)
952 Result ^= Result << 5 ^ N.GetHashCode();
953 }
954
955 return Result;
956 }
957
962 public void SetParent(ScriptNode Parent)
963 {
964 if (!(this.triples is null))
965 {
966 foreach (ISemanticTriple T in this.triples)
967 {
969 S.Node.SetParent(Parent);
970
972 P.Node.SetParent(Parent);
973
974 if (T.Object is SemanticScriptElement O)
975 O.Node.SetParent(Parent);
976 }
977 }
978
979 if (!(this.boundVariables is null))
980 {
981 foreach (KeyValuePair<ScriptNode, ScriptNode> P in this.boundVariables)
982 {
983 P.Key.SetParent(Parent);
984 P.Value.SetParent(Parent);
985 }
986 }
987
988 if (!(this.filter is null))
989 {
990 foreach (IFilterNode P in this.filter)
991 P.ScriptNode.SetParent(Parent);
992 }
993 }
994 }
995}
Node referencing a chunk in a ChunkedList<T>
Definition: ChunkNode.cs:11
ChunkNode< T > Next
Next chunk
Definition: ChunkNode.cs:26
int Pos
Index after the last element in chunk.
Definition: ChunkNode.cs:51
int Start
Index of first element in chunk.
Definition: ChunkNode.cs:46
A chunked list is a linked list of chunks of objects of type T .
Definition: ChunkedList.cs:54
IEnumerator< T > GetEnumerator()
Returns an enumerator for the collection.
Definition: ChunkedList.cs:418
ChunkNode< T > FirstChunk
First chunk
Definition: ChunkedList.cs:259
int Count
Number of elements in collection.
Definition: ChunkedList.cs:68
void Add(T Item)
Adds an item to the collection.
Definition: ChunkedList.cs:272
Base class for all nodes in a parsed script tree.
Definition: ScriptNode.cs:69
Represents a variable reference.
void AddFilter(ScriptNode Filter)
Adds a filter to the pattern.
void SetParent(ScriptNode Parent)
Sets the parent node. Can only be used when expression is being parsed or created.
void AddTriple(SemanticQueryTriple Triple)
Adds a triple to the pattern
ChunkedList< SemanticQueryTriple > Triples
Triples, null if none.
bool ForAllChildNodes(ScriptNodeEventHandler Callback, object State, SearchMethod Order)
Calls the callback method for all child nodes.
SparqlRegularPattern()
Represents a pattern in a SPARQL query.
Task< IEnumerable< Possibility > > Search(ISemanticCube Cube, Variables Variables, SparqlQuery Query)
Searches for the pattern on information in a semantic cube.
async Task< IEnumerable< Possibility > > Search(ISemanticCube Cube, Variables Variables, IEnumerable< Possibility > ExistingMatches, SparqlQuery Query)
Searches for the pattern on information in a semantic cube.
bool ForAll(ScriptNodeEventHandler Callback, object State, SearchMethod Order)
Calls the callback method for all child nodes.
void AddVariableBinding(ScriptNode Value, ScriptNode Variable)
Adds a variable binding to the pattern.
IEnumerable< IFilterNode > Filter
Filter, null if none.
IEnumerable< KeyValuePair< ScriptNode, ScriptNode > > BoundVariables
Bound variables, null if none.
Represents a possible solution during SPARQL evaluation.
Definition: Possibility.cs:13
ISemanticElement GetValue(string VariableName)
Access to possible variable values, given a variable name.
Definition: Possibility.cs:68
string VariableName(int Index)
Gets a variable name, given the axis index: 0=Subject, 1=Predicate, 2=Object.
string PredicateVariable
Predicate element variable name, if any
string ObjectVariable
Object element variable name, if any
string SubjectVariable
Subject element variable name, if any
Contains information about a variable.
Definition: Variable.cs:10
Collection of variables.
Definition: Variables.cs:25
Interface for semantic cubes.
Task< IEnumerable< ISemanticTriple > > GetTriples(ISemanticElement Value, int AxisIndex)
Gets available triples in the cube, having a given value, along a given axis.
Task< IEnumerable< ISemanticTriple > > GetTriplesBySubjectAndPredicateAndObject(ISemanticElement Subject, ISemanticElement Predicate, ISemanticElement Object)
Gets available triples in the cube, having a given subject, predicate and object.
Interface for semantic nodes.
Interface for semantic planes.
Interface for semantic triples.
ISemanticElement Object
Object element
ISemanticElement Predicate
Predicate element
ISemanticElement Subject
Subject element
delegate bool ScriptNodeEventHandler(ScriptNode Node, out ScriptNode NewNode, object State)
Delegate for ScriptNode callback methods.
SearchMethod
Method to traverse the expression structure
Definition: ScriptNode.cs:38