@@ -308,6 +308,37 @@ def ==(other)
308308 end
309309 alias_method :=== , :==
310310
311+ ##
312+ # Compares `self` to `other` for sorting purposes (with type check).
313+ #
314+ # @param [Object] other
315+ # @return [Integer] `-1`, `0`, or `1`
316+ def <=>( other )
317+ case other
318+ when Literal
319+ case
320+ when self . eql? ( other )
321+ 0
322+ when self . language? && other . language?
323+ # Literals with languages can compare if languages are identical
324+ self . to_s <=> other . to_s
325+ when self . simple? && other . simple?
326+ self . to_s <=> other . to_s
327+ when !self . valid?
328+ type_error ( "#{ self . inspect } is invalid" ) || 0
329+ when !other . valid?
330+ type_error ( "#{ other . inspect } is invalid" ) || 0
331+ when self . comperable_datatype2? ( other )
332+ self . object <=> other . object
333+ else
334+ type_error ( "#{ self . inspect } and #{ other . inspect } are not comperable" ) || 0
335+ end
336+ when String
337+ self . simple? && self . value <=> other
338+ else 1
339+ end
340+ end
341+
311342 ##
312343 # Returns `true` if this is a plain literal. A plain literal
313344 # may have a language, but may not have a datatype. For
@@ -399,6 +430,32 @@ def comperable_datatype?(other)
399430 end
400431 end
401432
433+ ##
434+ # Returns `true` if the literal has a datatype and the comparison should
435+ # return false instead of raise a type error.
436+ #
437+ # Used for <=> operator.
438+ #
439+ # This behavior is intuited from SPARQL data-r2/expr-equal/eq-2-2
440+ # @return [Boolean]
441+ def comperable_datatype2? ( other )
442+ case self
443+ when RDF ::Literal ::Numeric , RDF ::Literal ::Boolean
444+ case other
445+ when RDF ::Literal ::Numeric , RDF ::Literal ::Boolean
446+ true
447+ else
448+ self . plain? || other . plain? ||
449+ self . language? || other . language? ||
450+ self . datatype == other . datatype
451+ end
452+ else
453+ self . plain? || other . plain? ||
454+ self . language? || other . language? ||
455+ self . datatype == other . datatype
456+ end
457+ end
458+
402459 ##
403460 # Converts this literal into its canonical lexical representation.
404461 #
0 commit comments