rdf-n3 3.1.1 → 3.1.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (124) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +148 -69
  3. data/UNLICENSE +1 -1
  4. data/VERSION +1 -1
  5. data/lib/rdf/n3.rb +8 -8
  6. data/lib/rdf/n3/algebra.rb +147 -68
  7. data/lib/rdf/n3/algebra/builtin.rb +79 -0
  8. data/lib/rdf/n3/algebra/formula.rb +355 -94
  9. data/lib/rdf/n3/algebra/list/append.rb +33 -4
  10. data/lib/rdf/n3/algebra/list/first.rb +24 -0
  11. data/lib/rdf/n3/algebra/list/in.rb +42 -3
  12. data/lib/rdf/n3/algebra/list/last.rb +17 -4
  13. data/lib/rdf/n3/algebra/list/length.rb +24 -0
  14. data/lib/rdf/n3/algebra/list/member.rb +39 -2
  15. data/lib/rdf/n3/algebra/list_operator.rb +83 -0
  16. data/lib/rdf/n3/algebra/log/conclusion.rb +57 -1
  17. data/lib/rdf/n3/algebra/log/conjunction.rb +28 -1
  18. data/lib/rdf/n3/algebra/log/content.rb +34 -0
  19. data/lib/rdf/n3/algebra/log/equal_to.rb +34 -0
  20. data/lib/rdf/n3/algebra/log/implies.rb +55 -30
  21. data/lib/rdf/n3/algebra/log/includes.rb +58 -1
  22. data/lib/rdf/n3/algebra/log/n3_string.rb +34 -0
  23. data/lib/rdf/n3/algebra/log/not_equal_to.rb +23 -0
  24. data/lib/rdf/n3/algebra/log/not_includes.rb +27 -0
  25. data/lib/rdf/n3/algebra/log/output_string.rb +40 -0
  26. data/lib/rdf/n3/algebra/log/parsed_as_n3.rb +36 -0
  27. data/lib/rdf/n3/algebra/log/semantics.rb +40 -0
  28. data/lib/rdf/n3/algebra/math/absolute_value.rb +36 -0
  29. data/lib/rdf/n3/algebra/math/acos.rb +26 -0
  30. data/lib/rdf/n3/algebra/math/acosh.rb +26 -0
  31. data/lib/rdf/n3/algebra/math/asin.rb +26 -0
  32. data/lib/rdf/n3/algebra/math/asinh.rb +26 -0
  33. data/lib/rdf/n3/algebra/math/atan.rb +26 -0
  34. data/lib/rdf/n3/algebra/math/atanh.rb +26 -0
  35. data/lib/rdf/n3/algebra/math/ceiling.rb +28 -0
  36. data/lib/rdf/n3/algebra/math/cos.rb +40 -0
  37. data/lib/rdf/n3/algebra/math/cosh.rb +38 -0
  38. data/lib/rdf/n3/algebra/math/difference.rb +34 -3
  39. data/lib/rdf/n3/algebra/math/equal_to.rb +54 -0
  40. data/lib/rdf/n3/algebra/math/exponentiation.rb +29 -3
  41. data/lib/rdf/n3/algebra/math/floor.rb +28 -0
  42. data/lib/rdf/n3/algebra/math/greater_than.rb +41 -0
  43. data/lib/rdf/n3/algebra/math/less_than.rb +41 -0
  44. data/lib/rdf/n3/algebra/math/negation.rb +31 -2
  45. data/lib/rdf/n3/algebra/math/not_equal_to.rb +25 -0
  46. data/lib/rdf/n3/algebra/math/not_greater_than.rb +25 -0
  47. data/lib/rdf/n3/algebra/math/not_less_than.rb +25 -0
  48. data/lib/rdf/n3/algebra/math/product.rb +14 -3
  49. data/lib/rdf/n3/algebra/math/quotient.rb +30 -3
  50. data/lib/rdf/n3/algebra/math/remainder.rb +29 -3
  51. data/lib/rdf/n3/algebra/math/rounded.rb +20 -3
  52. data/lib/rdf/n3/algebra/math/sin.rb +40 -0
  53. data/lib/rdf/n3/algebra/math/sinh.rb +38 -0
  54. data/lib/rdf/n3/algebra/math/sum.rb +35 -4
  55. data/lib/rdf/n3/algebra/math/tan.rb +40 -0
  56. data/lib/rdf/n3/algebra/math/tanh.rb +38 -0
  57. data/lib/rdf/n3/algebra/not_implemented.rb +13 -0
  58. data/lib/rdf/n3/algebra/resource_operator.rb +123 -0
  59. data/lib/rdf/n3/algebra/str/concatenation.rb +21 -3
  60. data/lib/rdf/n3/algebra/str/contains.rb +28 -4
  61. data/lib/rdf/n3/algebra/str/contains_ignoring_case.rb +33 -0
  62. data/lib/rdf/n3/algebra/str/ends_with.rb +33 -0
  63. data/lib/rdf/n3/algebra/str/equal_ignoring_case.rb +34 -0
  64. data/lib/rdf/n3/algebra/str/format.rb +12 -4
  65. data/lib/rdf/n3/algebra/str/greater_than.rb +38 -0
  66. data/lib/rdf/n3/algebra/str/less_than.rb +33 -0
  67. data/lib/rdf/n3/algebra/str/matches.rb +33 -5
  68. data/lib/rdf/n3/algebra/str/not_equal_ignoring_case.rb +17 -0
  69. data/lib/rdf/n3/algebra/str/not_greater_than.rb +17 -0
  70. data/lib/rdf/n3/algebra/str/not_less_than.rb +17 -0
  71. data/lib/rdf/n3/algebra/str/not_matches.rb +18 -0
  72. data/lib/rdf/n3/algebra/str/replace.rb +28 -5
  73. data/lib/rdf/n3/algebra/str/scrape.rb +31 -5
  74. data/lib/rdf/n3/algebra/str/starts_with.rb +33 -0
  75. data/lib/rdf/n3/algebra/time/day.rb +35 -0
  76. data/lib/rdf/n3/algebra/time/day_of_week.rb +27 -0
  77. data/lib/rdf/n3/algebra/time/gm_time.rb +29 -0
  78. data/lib/rdf/n3/algebra/time/hour.rb +35 -0
  79. data/lib/rdf/n3/algebra/time/in_seconds.rb +59 -0
  80. data/lib/rdf/n3/algebra/time/local_time.rb +29 -0
  81. data/lib/rdf/n3/algebra/time/minute.rb +35 -0
  82. data/lib/rdf/n3/algebra/time/month.rb +35 -0
  83. data/lib/rdf/n3/algebra/time/second.rb +35 -0
  84. data/lib/rdf/n3/algebra/time/timezone.rb +36 -0
  85. data/lib/rdf/n3/algebra/time/year.rb +29 -0
  86. data/lib/rdf/n3/extensions.rb +180 -21
  87. data/lib/rdf/n3/format.rb +65 -0
  88. data/lib/rdf/n3/list.rb +630 -0
  89. data/lib/rdf/n3/reader.rb +762 -485
  90. data/lib/rdf/n3/reasoner.rb +57 -68
  91. data/lib/rdf/n3/refinements.rb +178 -0
  92. data/lib/rdf/n3/repository.rb +332 -0
  93. data/lib/rdf/n3/terminals.rb +80 -0
  94. data/lib/rdf/n3/vocab.rb +35 -7
  95. data/lib/rdf/n3/writer.rb +208 -148
  96. metadata +110 -52
  97. data/AUTHORS +0 -1
  98. data/History.markdown +0 -99
  99. data/lib/rdf/n3/algebra/log/equalTo.rb +0 -7
  100. data/lib/rdf/n3/algebra/log/notEqualTo.rb +0 -7
  101. data/lib/rdf/n3/algebra/log/notIncludes.rb +0 -12
  102. data/lib/rdf/n3/algebra/log/outputString.rb +0 -7
  103. data/lib/rdf/n3/algebra/math/absoluteValue.rb +0 -9
  104. data/lib/rdf/n3/algebra/math/equalTo.rb +0 -9
  105. data/lib/rdf/n3/algebra/math/greaterThan.rb +0 -9
  106. data/lib/rdf/n3/algebra/math/integerQuotient.rb +0 -9
  107. data/lib/rdf/n3/algebra/math/lessThan.rb +0 -9
  108. data/lib/rdf/n3/algebra/math/memberCount.rb +0 -9
  109. data/lib/rdf/n3/algebra/math/notEqualTo.rb +0 -9
  110. data/lib/rdf/n3/algebra/math/notGreaterThan.rb +0 -9
  111. data/lib/rdf/n3/algebra/math/notLessThan.rb +0 -9
  112. data/lib/rdf/n3/algebra/str/containsIgnoringCase.rb +0 -9
  113. data/lib/rdf/n3/algebra/str/endsWith.rb +0 -9
  114. data/lib/rdf/n3/algebra/str/equalIgnoringCase.rb +0 -9
  115. data/lib/rdf/n3/algebra/str/greaterThan.rb +0 -9
  116. data/lib/rdf/n3/algebra/str/lessThan.rb +0 -9
  117. data/lib/rdf/n3/algebra/str/notEqualIgnoringCase.rb +0 -9
  118. data/lib/rdf/n3/algebra/str/notGreaterThan.rb +0 -9
  119. data/lib/rdf/n3/algebra/str/notLessThan.rb +0 -9
  120. data/lib/rdf/n3/algebra/str/notMatches.rb +0 -9
  121. data/lib/rdf/n3/algebra/str/startsWith.rb +0 -56
  122. data/lib/rdf/n3/patches/array_hacks.rb +0 -53
  123. data/lib/rdf/n3/reader/meta.rb +0 -641
  124. data/lib/rdf/n3/reader/parser.rb +0 -239
@@ -0,0 +1,34 @@
1
+ module RDF::N3::Algebra::Log
2
+ ##
3
+ # True if the subject and object are the same RDF node (symbol or literal). Do not confuse with owl:sameAs. A cwm built-in logical operator, RDF graph level.
4
+ class EqualTo < RDF::N3::Algebra::ResourceOperator
5
+ NAME = :logEqualTo
6
+ URI = RDF::N3::Log.equalTo
7
+
8
+ ##
9
+ # Resolves inputs as terms.
10
+ #
11
+ # @param [RDF::Term] resource
12
+ # @param [:subject, :object] position
13
+ # @return [RDF::Literal]
14
+ # @see RDF::N3::ResourceOperator#evaluate
15
+ def resolve(resource, position:)
16
+ resource if resource.term?
17
+ end
18
+
19
+ # Both subject and object are inputs.
20
+ def input_operand
21
+ RDF::N3::List.new(values: operands)
22
+ end
23
+
24
+ ##
25
+ # @param [RDF::Literal] left
26
+ # a literal
27
+ # @param [RDF::Literal] right
28
+ # a literal
29
+ # @return [RDF::Literal::Boolean]
30
+ def apply(left, right)
31
+ RDF::Literal(left.sameTerm?(right))
32
+ end
33
+ end
34
+ end
@@ -8,12 +8,15 @@ module RDF::N3::Algebra::Log
8
8
  class Implies < SPARQL::Algebra::Operator::Binary
9
9
  include SPARQL::Algebra::Query
10
10
  include SPARQL::Algebra::Update
11
- include RDF::Enumerable
12
- include RDF::Util::Logger
11
+ include RDF::N3::Algebra::Builtin
13
12
 
14
13
  NAME = :logImplies
14
+ URI = RDF::N3::Log.implies
15
15
 
16
- # Yields solutions from subject. Solutions are created by evaluating subject against `queryable`.
16
+ ##
17
+ # Returns solutions from subject. Solutions are created by evaluating subject against `queryable`.
18
+ #
19
+ # Solutions are kept within this instance, and used for conclusions. Note that the evaluated solutions do not affect that of the invoking formula, as the solution spaces are disjoint.
17
20
  #
18
21
  # @param [RDF::Queryable] queryable
19
22
  # the graph or repository to query
@@ -24,14 +27,44 @@ module RDF::N3::Algebra::Log
24
27
  # @return [RDF::Solutions] distinct solutions
25
28
  def execute(queryable, solutions:, **options)
26
29
  @queryable = queryable
27
- log_debug {"logImplies"}
28
- @solutions = log_depth {operands.first.execute(queryable, solutions: solutions, **options)}
29
- log_debug {"(logImplies solutions) #{@solutions.to_sxp}"}
30
+ @solutions = RDF::Query::Solutions(solutions.map do |solution|
31
+ log_debug(NAME, "solution") {SXP::Generator.string(solution.to_sxp_bin)}
32
+ subject = operand(0).evaluate(solution.bindings, formulae: formulae)
33
+ object = operand(1).evaluate(solution.bindings, formulae: formulae)
34
+ log_info(NAME, "subject") {SXP::Generator.string(subject.to_sxp_bin)}
35
+ log_info(NAME, "object") {SXP::Generator.string(object.to_sxp_bin)}
36
+
37
+ # Nothing to do if variables aren't resolved.
38
+ next unless subject && object
39
+
40
+ solns = log_depth {subject.execute(queryable, solutions: RDF::Query::Solutions(solution), **options)}
41
+
42
+ # Execute object as well (typically used for log:outputString)
43
+ solns.each do |soln|
44
+ log_depth {object.execute(queryable, solutions: RDF::Query::Solutions(soln), **options)}
45
+ end
46
+
47
+ # filter solutions where not all variables in antecedant are bound.
48
+ vars = subject.universal_vars
49
+ solns = RDF::Query::Solutions(solns.to_a.select do |soln|
50
+ vars.all? {|v| soln.bound?(v)}
51
+ end)
52
+ solns
53
+ end.flatten.compact.uniq)
54
+ log_info(NAME) {SXP::Generator.string(@solutions.to_sxp_bin)}
30
55
 
31
56
  # Return original solutions, without bindings
32
57
  solutions
33
58
  end
34
59
 
60
+ ##
61
+ # Clear out any cached solutions.
62
+ # This principaly is for log:conclusions
63
+ def clear_solutions
64
+ super
65
+ @solutions = nil
66
+ end
67
+
35
68
  ##
36
69
  # Yields statements from the object based on solutions determined from the subject. Each solution formed by querying `queryable` from the subject is used to create a graph, which must be a subgraph of `queryable`. If so, that solution is used to generate triples from the object formula which are yielded.
37
70
  #
@@ -39,34 +72,26 @@ module RDF::N3::Algebra::Log
39
72
  # each matching statement
40
73
  # @yieldparam [RDF::Statement] solution
41
74
  # @yieldreturn [void] ignored
42
- def each(&block)
43
- @solutions ||= RDF::Query::Solutions.new
44
- log_debug {"logImplies each #{@solutions.to_sxp}"}
45
- subject, object = operands
46
-
47
- if @solutions.empty?
48
- # Some evalaluatable operand evaluated to false
49
- log_debug("(logImplies implication false - no solutions)")
50
- return
51
- end
52
-
53
- # Graph based on solutions from subject
54
- subject_graph = log_depth {RDF::Graph.new {|g| g << subject}}
75
+ def each(solutions: RDF::Query::Solutions(), &block)
76
+ # Merge solutions in with those for the evaluation of this implication
77
+ # Clear out solutions so they don't get remembered erroneously.
78
+ solutions, @solutions = Array(@solutions), nil
79
+ log_depth do
80
+ super(solutions: RDF::Query::Solutions(RDF::Query::Solution.new), &block)
55
81
 
56
- # Use solutions from subject for object
57
- object.solutions = @solutions
82
+ solutions.each do |solution|
83
+ log_info("(logImplies each) solution") {SXP::Generator.string solution.to_sxp_bin}
84
+ object = operand(1).evaluate(solution.bindings, formulae: formulae)
85
+ log_info("(logImplies each) object") {SXP::Generator.string object.to_sxp_bin}
58
86
 
59
- # Nothing emitted if @solutions is not complete. Solutions are complete when all variables are bound.
60
- if @queryable.contain?(subject_graph)
61
- log_debug("(logImplies implication true)")
62
- # Yield statements into the default graph
63
- log_depth do
64
- object.each do |statement|
65
- block.call(RDF::Statement.from(statement.to_triple, inferred: true, graph_name: graph_name))
87
+ # Yield inferred statements
88
+ log_depth do
89
+ object.each(solutions: RDF::Query::Solutions(solution)) do |statement|
90
+ log_debug(("(logImplies each) infer\s")) {statement.to_sxp}
91
+ block.call(RDF::Statement.from(statement.to_quad, inferred: true))
92
+ end
66
93
  end
67
94
  end
68
- else
69
- log_debug("(logImplies implication false)")
70
95
  end
71
96
  end
72
97
 
@@ -7,7 +7,64 @@ module RDF::N3::Algebra::Log
7
7
  # Variable substitution is applied recursively to nested compound terms such as formulae, lists and sets.
8
8
  #
9
9
  # (Understood natively by cwm when in in the antecedent of a rule. You can use this to peer inside nested formulae.)
10
- class Includes < SPARQL::Algebra::Operator::Binary
10
+ class Includes < RDF::N3::Algebra::ResourceOperator
11
11
  NAME = :logIncludes
12
+ URI = RDF::N3::Log.includes
13
+
14
+ ##
15
+ # Both subject and object must be formulae.
16
+ #
17
+ # @param [RDF::Term] resource
18
+ # @param [:subject, :object] position
19
+ # @return [RDF::Term]
20
+ # @see RDF::N3::ResourceOperator#evaluate
21
+ def resolve(resource, position:)
22
+ resource if resource.formula?
23
+ end
24
+
25
+ # Both subject and object are inputs.
26
+ def input_operand
27
+ RDF::N3::List.new(values: operands)
28
+ end
29
+
30
+ ##
31
+ # Creates a repository constructed by substituting variables and in that subject with known IRIs and queries object against that repository. Either retuns a single solution, or no solutions.
32
+ #
33
+ # @note this does allow object to have variables not in the subject, if they could have been substituted away.
34
+ #
35
+ # @param [RDF::N3::Algebra::Formula] subject
36
+ # a formula
37
+ # @param [RDF::N3::Algebra::Formula] object
38
+ # a formula
39
+ # @return [RDF::Literal::Boolean]
40
+ def apply(subject, object)
41
+ subject_var_map = subject.variables.values.inject({}) {|memo, v| memo.merge(v => RDF::URI(v.name))}
42
+ object_vars = object.variables.keys
43
+ log_debug(NAME, "subject var map") {SXP::Generator.string(subject_var_map.to_sxp_bin)}
44
+ log_debug(NAME, "object vars") {SXP::Generator.string(object_vars.to_sxp_bin)}
45
+ # create a queryable from subject, replacing variables with IRIs for thsoe variables.
46
+ queryable = RDF::Repository.new do |r|
47
+ log_depth do
48
+ subject.each do |stmt|
49
+ parts = stmt.to_quad.map do |part|
50
+ part.is_a?(RDF::Query::Variable) ? subject_var_map.fetch(part) : part
51
+ end
52
+ r << RDF::Statement.from(parts)
53
+ end
54
+ end
55
+ end
56
+
57
+ # Query object against subject
58
+ solns = log_depth {queryable.query(object, **@options)}
59
+ log_info("(#{NAME} solutions)") {SXP::Generator.string solns.to_sxp_bin}
60
+
61
+ if !solns.empty? && (object_vars - solns.variable_names).empty?
62
+ # Return solution
63
+ solns.first
64
+ else
65
+ # Return false,
66
+ RDF::Literal::FALSE
67
+ end
68
+ end
12
69
  end
13
70
  end
@@ -0,0 +1,34 @@
1
+ module RDF::N3::Algebra::Log
2
+ ##
3
+ # The subject formula, expressed as N3, gives this string.
4
+ class N3String < RDF::N3::Algebra::ResourceOperator
5
+ NAME = :logN3String
6
+ URI = RDF::N3::Log.n3String
7
+
8
+ ##
9
+ # Serializes the subject formula into an N3 string representation.
10
+ #
11
+ # @param [RDF::N3::List] resource
12
+ # @return [RDF::Term]
13
+ def resolve(resource, position: :subject)
14
+ case position
15
+ when :subject
16
+ return nil unless resource.formula?
17
+ as_literal(RDF::N3::Writer.buffer {|w| resource.each {|st| w << st}})
18
+ when :object
19
+ return nil unless resource.literal? || resource.variable?
20
+ resource
21
+ end
22
+ end
23
+
24
+ ##
25
+ # Subject must evaluate to a formula and object to a literal.
26
+ #
27
+ # @param [RDF::Term] subject
28
+ # @param [RDF::Term] object
29
+ # @return [Boolean]
30
+ def valid?(subject, object)
31
+ subject.formula? && (object.variable? || object.literal?)
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,23 @@
1
+ module RDF::N3::Algebra::Log
2
+ ##
3
+ # Equality in this sense is actually the same URI. A cwm built-in logical operator.
4
+ class NotEqualTo < SPARQL::Algebra::Operator::SameTerm
5
+ include RDF::N3::Algebra::Builtin
6
+ NAME = :logNotEqualTo
7
+ URI = RDF::N3::Log.notEqualto
8
+
9
+ ##
10
+ # Returns `true` if the operands are not the same RDF term; returns
11
+ # `false` otherwise.
12
+ #
13
+ # @param [RDF::Term] term1
14
+ # an RDF term
15
+ # @param [RDF::Term] term2
16
+ # an RDF term
17
+ # @return [RDF::Literal::Boolean] `true` or `false`
18
+ # @raise [TypeError] if either operand is unbound
19
+ def apply(term1, term2)
20
+ RDF::Literal(!term1.eql?(term2))
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,27 @@
1
+ module RDF::N3::Algebra::Log
2
+ ##
3
+ # The object formula is NOT a subset of subject. True iff log:includes is false. The converse of log:includes.
4
+ # (Understood natively by cwm. The subject formula may contain variables.)
5
+ #
6
+ # (In cwm, variables must of course end up getting bound before the log:include test can be done, or an infinite result set would result)
7
+ #
8
+ # Related: See includes
9
+ class NotIncludes < Includes
10
+ NAME = :logNotIncludes
11
+ URI = RDF::N3::Log.notIncludes
12
+
13
+ ##
14
+ # Uses log:includes and returns a solution if log:includes fails
15
+ #
16
+ # @param [RDF::Queryable] queryable
17
+ # the graph or repository to query
18
+ # @param [Hash{Symbol => Object}] options
19
+ # any additional keyword options
20
+ # @option options [RDF::Query::Solutions] solutions
21
+ # optional initial solutions for chained queries
22
+ # @return [RDF::Solutions] distinct solutions
23
+ def execute(queryable, solutions:, **options)
24
+ super.empty? ? RDF::Query::Solutions(RDF::Query::Solution.new) : RDF::Query::Solutions.new
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,40 @@
1
+ module RDF::N3::Algebra::Log
2
+ ##
3
+ # The subject is a key and the object is a string, where the strings are to be output in the order of the keys.
4
+ class OutputString < RDF::N3::Algebra::ResourceOperator
5
+ NAME = :logOutputString
6
+ URI = RDF::N3::Log.outputString
7
+
8
+ ##
9
+ # Resolves inputs as strings.
10
+ #
11
+ # @param [RDF::Term] resource
12
+ # @param [:subject, :object] position
13
+ # @return [RDF::Term]
14
+ # @see RDF::N3::ResourceOperator#evaluate
15
+ def resolve(resource, position:)
16
+ SPARQL::Algebra::Expression.cast(RDF::XSD.string, resource) if resource.term?
17
+ end
18
+
19
+ ##
20
+ # Returns `term2`, but adds `term2` as an output keyed on `term1`.
21
+ #
22
+ # @param [RDF::Term] term1
23
+ # an RDF term
24
+ # @param [RDF::Term] term2
25
+ # an RDF term
26
+ # @return [RDF::Literal::Boolean] `true` or `false`
27
+ # @raise [TypeError] if either operand is not an RDF term or operands are not comperable
28
+ #
29
+ # @see RDF::Term#==
30
+ def apply(term1, term2)
31
+ (@options[:strings][term1.to_s] ||= []) << term2.to_s
32
+ term2
33
+ end
34
+
35
+ # Both subject and object are inputs.
36
+ def input_operand
37
+ RDF::N3::List.new(values: operands)
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,36 @@
1
+ module RDF::N3::Algebra::Log
2
+ ##
3
+ # The subject string, parsed as N3, gives this formula.
4
+ class ParsedAsN3 < RDF::N3::Algebra::ResourceOperator
5
+ NAME = :logParsedAsN3
6
+ URI = RDF::N3::Log.parsedAsN3
7
+
8
+ ##
9
+ # Parses the subject into a new formula.
10
+ #
11
+ # Returns nil if resource does not validate, given its position
12
+ #
13
+ # @param [RDF::N3::List] resource
14
+ # @return [RDF::Term]
15
+ def resolve(resource, position: :subject)
16
+ case position
17
+ when :subject
18
+ return nil unless resource.literal?
19
+ begin
20
+ repo = RDF::N3::Repository.new
21
+ repo << RDF::N3::Reader.new(resource.to_s, **@options.merge(list_terms: true, logger: false))
22
+ log_debug("logParsedAsN3") {SXP::Generator.string repo.statements.to_sxp_bin}
23
+ content_hash = resource.hash # used as name of resulting formula
24
+ form = RDF::N3::Algebra::Formula.from_enumerable(repo, graph_name: RDF::Node.intern(content_hash))
25
+ log_info(NAME) {"form hash (#{resource}): #{form.hash}"}
26
+ form
27
+ rescue RDF::ReaderError
28
+ nil
29
+ end
30
+ when :object
31
+ return nil unless resource.literal? || resource.is_a?(RDF::Query::Variable)
32
+ resource
33
+ end
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,40 @@
1
+ module RDF::N3::Algebra::Log
2
+ ##
3
+ # The log:semantics of a document is the formula. achieved by parsing representation of the document. For a document in Notation3, log:semantics is the log:parsedAsN3 of the log:contents of the document. For a document in RDF/XML, it is parsed according to the RDF/XML specification to yield an RDF formula (a subclass of N3 log:Formula).
4
+ #
5
+ # [Aside: Philosophers will be distracted here into worrying about the meaning of meaning. At least we didn't call this function "meaning"! In as much as N3 is used as an interlingua for interoperability for different systems, this for an N3 based system is the meaning expressed by a document.]
6
+ #
7
+ # (Cwm knows how to go get a document and parse N3 and RDF/XML it in order to evaluate this. Other languages for web documents may be defined whose N3 semantics are therefore also calculable, and so they could be added in due course. See for example GRDDL, RDFa, etc)
8
+ class Semantics < RDF::N3::Algebra::ResourceOperator
9
+ NAME = :logSemantics
10
+ URI = RDF::N3::Log.semantics
11
+
12
+ ##
13
+ # Parses the subject into a new formula.
14
+ #
15
+ # Returns nil if resource does not validate, given its position
16
+ #
17
+ # @param [RDF::N3::List] resource
18
+ # @return [RDF::Term]
19
+ def resolve(resource, position: :subject)
20
+ case position
21
+ when :subject
22
+ return nil unless resource.literal? || resource.uri?
23
+ begin
24
+ repo = RDF::N3::Repository.new
25
+ repo << RDF::Reader.open(resource, **@options.merge(list_terms: true, base_uri: resource, logger: false))
26
+ content_hash = repo.statements.hash # used as name of resulting formula
27
+ form = RDF::N3::Algebra::Formula.from_enumerable(repo, graph_name: RDF::Node.intern(content_hash))
28
+ log_debug(NAME) {"form hash (#{resource}): #{form.hash}"}
29
+ form
30
+ rescue IOError, RDF::ReaderError => e
31
+ log_error(NAME) {"error loading #{resource}: #{e}"}
32
+ nil
33
+ end
34
+ when :object
35
+ return nil unless resource.literal? || resource.variable?
36
+ resource
37
+ end
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,36 @@
1
+ module RDF::N3::Algebra::Math
2
+ ##
3
+ # The object is calulated as the absolute value of the subject.
4
+ #
5
+ # @see https://www.w3.org/TR/xpath-functions/#func-abs
6
+ class AbsoluteValue < RDF::N3::Algebra::ResourceOperator
7
+ NAME = :mathAbsoluteValue
8
+ URI = RDF::N3::Math.absoluteValue
9
+
10
+ ##
11
+ # The math:absoluteValue operator takes string or number and calculates its absolute value.
12
+ #
13
+ # @param [RDF::Term] resource
14
+ # @param [:subject, :object] position
15
+ # @return [RDF::Term]
16
+ # @see RDF::N3::ResourceOperator#evaluate
17
+ def resolve(resource, position:)
18
+ case position
19
+ when :subject
20
+ return nil unless resource.literal?
21
+ as_literal(resource.as_number.abs)
22
+ when :object
23
+ return nil unless resource.literal? || resource.variable?
24
+ resource
25
+ end
26
+ end
27
+
28
+ ##
29
+ # Input is either the subject or object
30
+ #
31
+ # @return [RDF::Term]
32
+ def input_operand
33
+ RDF::N3::List.new(values: operands)
34
+ end
35
+ end
36
+ end