matching method

RdfGraph matching({
  1. RdfSubject? subject,
  2. RdfPredicate? predicate,
  3. RdfObject? object,
})

Creates a new graph containing only triples that match the given pattern

This method returns a filtered graph containing all triples that match the specified pattern components. Unlike findTriples, this method returns a new RdfGraph instance that can be used for further graph operations, chaining, and merging.

Performance Optimization: When filtering by subject (with or without predicate) and indexing is enabled, this method can reuse parts of the existing index for improved performance of subsequent operations on the filtered graph.

Pattern matching uses AND logic - all non-null parameters must match for a triple to be included. Null parameters act as wildcards and match any value in that position.

Parameters:

  • subject Optional subject to match (null acts as wildcard)
  • predicate Optional predicate to match (null acts as wildcard)
  • object Optional object to match (null acts as wildcard)

Returns: A new RdfGraph containing only the matching triples. The filtered graph may be empty if no triples match the pattern.

Example:

// Get all information about John as a separate graph
final johnGraph = graph.matching(subject: john);

// Get all type declarations
final typeGraph = graph.matching(predicate: rdf.type);

// Chain operations efficiently
final result = graph
  .matching(subject: john)
  .merge(otherGraph)
  .matching(predicate: foaf.knows);

Implementation

RdfGraph matching({
  RdfSubject? subject,
  RdfPredicate? predicate,
  RdfObject? object,
}) {
  // Optimization: if filtering by subject and we have an index
  if (subject != null && object == null) {
    switch (_effectiveIndex) {
      case null:
        break;
      case final index:
        final subjectMap = index[subject];
        if (subjectMap == null) {
          // Subject not found - return empty graph
          return RdfGraph(enableIndexing: indexingEnabled);
        }

        if (predicate == null) {
          // Subject only: use entire subject map
          final subjectTriples = subjectMap.values.expand((list) => list);
          final reducedIndex = {subject: subjectMap};

          return RdfGraph._withIndex(
            subjectTriples,
            reducedIndex,
            indexingEnabled,
          );
        } else {
          // Subject + predicate: use specific predicate list
          final predicateTriples = subjectMap[predicate];
          if (predicateTriples == null) {
            // Subject+predicate not found - return empty graph
            return RdfGraph(enableIndexing: indexingEnabled);
          }

          final reducedIndex = {
            subject: {predicate: predicateTriples}
          };

          return RdfGraph._withIndex(
            predicateTriples,
            reducedIndex,
            indexingEnabled,
          );
        }
    }
  }

  // General case: delegate to findTriples and create new graph
  final matchingTriples = findTriples(
    subject: subject,
    predicate: predicate,
    object: object,
  );

  return RdfGraph(triples: matchingTriples, enableIndexing: indexingEnabled);
}