Re: !=, NOT IN and type errors

* Jeen Broekstra <jeen.broekstra@gmail.com> [2011-03-27 10:59+1300]
> On 27/03/2011 00:40, Eric Prud'hommeaux wrote:
> 
> >I suspect that the issue lies with the way the way the operator
> >mapping is specified. §16.3 ¶1 says
> >[[
> >When selecting the operator definition for a given set of parameters,
> >the definition with the most specific parameters applies. … The table
> >is arranged so that the upper-most viable candiate is the most
> >specific. Operators invoked without appropriate operands result in a
> >type error.
> >]] — http://www.w3.org/TR/rdf-sparql-query/#OperatorMapping
> >
> >Entries for the supported "=" operands, e.g.
> >   A = B   numeric   numeric   op:numeric-equal(A, B)       xsd:boolean
> >preceed the catch-all
> >   A = B   RDF term  RDF term  RDFterm-equal(A, B)          xsd:boolean
> >   A != B  RDF term  RDF term  fn:not(RDFterm-equal(A, B))  xsd:boolean
> >
> >so RDFterm-equal is responsible only for non-literal terms and the
> >literals which are not known to be equivalent. The footnote to which
> >you refer is intended to help illustrate this effect, but doesn't
> >change the definition of RDFterm-equal (i.e. if they're both literal,
> >throw a type error).
> 
> Ok, I am officially confused now. I have the impression that what
> you say happens is not quite the same as what Andy says happens.
> 
> >§16.3.1 Operator Extensibility preceeds §16.4 Operator Definitions and
> >is intended to illustrate the effect of extending the set of operator
> >functions, the footnote illustrates the effects of extensibility on
> >how and when RDFterm-equal is called.
> >
> >With all of these fabulous candidates laid out in front of you, can
> >you suggest a change to one or more which will make this clearer?
> 
> I am probably still making a mistake somewhere, or we are all
> overlooking something. The former is more likely, so let me just go
> through a simple example case one step at a time, and you can stop
> me at the point where I make the error. That would likely be the
> point at which either I go "duh!" or you go "hmm, we could clarify
> that".
> 
> Example case: determine the truth value of the expression
> "foo"^^xsd:string != "4"^^xsd:integer.
> 
> Looking at the operator mapping table in 16.3 (17.3 in the editor's
> draft), let's see which mapping applies. The first mapping for !=
> is:
> 
>  A != B numeric numeric fn:not(op:numeric-equal(A, B)) xsd:boolean
> 
> This mapping does not apply because "foo"^^xsd:string can not be
> promoted/substituted to be a numerical literal.
> 
> Second:
> 
> A != B simple literal simple literal
> fn:not(op:numeric-equal(fn:compare(A, B), 0)) xsd:boolean
> 
> Does not apply because neither is a simple literal.
> 
> Third:
> 
> A !=
> B xsd:string xsd:string fn:not(op:numeric-equal(fn:compare(STR(A),
> STR(B)), 0)) xsd:boolean
> 
> Does not apply because "4"^^xsd:integer can not be
> promoted/substituted to xsd:string.
> 
> Fourth:
> 
> A != B xsd:boolean xsd:boolean fn:not(op:boolean-equal(A, B)) xsd:boolean
> 
> Does not apply either, neither can be promoted/substituted to boolean.
> 
> Fifth:
> 
> A != B xsd:dateTime xsd:dateTime fn:not(op:dateTime-equal(A, B)) xsd:boolean
> 
> Does not apply for the same reason.
> 
> Last:
> 
> A != B RDF term RDF term fn:not(RDFterm-equal(A, B)) xsd:boolean
> 
> So, in the case of comparing a string-typed literal with an
> int-typed one, we fall back on RDFterm-equal. Correct sofar?
> 
> Now, we apply RDFterm-equal to our comparison. Both operands are
> literals. The definition says that two literals are RDF-term-equal
> if they are "equivalent literals" according to def 6.5.1 in RDF
> concepts. Since our operands have different lexical values as well
> as different datatypes, literal equality fails. The definition of
> RDFterm-equal then says: "[it] produces a type error when both
> operands are literal but are not the same RDF term". Since in our
> case both are literal but are not the same term, it results in a
> type error. So RDFterm-equal results in a type error, and since
> applying fn:not on a type error results in a type error,
> "foo"^^xsd:string != "4"^^xsd:integer evaluates to a type error.
> This is what I originally thought happened, and what I thought was
> undesirable.

Ahh, this is what I believe to have been the design goal. The problem
is exemplified by
  "iiii"^^my:romanNumeral = "iv"^^my:romanNumeral

The answer there is probably a non-controversial "beats me". The
answer to "foo"^^xsd:string != "4"^^xsd:integer in unextended
implementations is also "beats me", but that doesn't keep you from
adding operators for e.g. xsd:string and xsd:integer for which the
answer to "=" is false. (You probably want a switch to enable you
to run the unextended tests, which have no way of distinnguishing
between sagely extension and wanton impudance.)

We could take the bold step of declaring the 19 native types pairwise
distinct by either adding a bazillion rows to the operator mapping or
expanding the definition of RDFterm-equal like so:
[[
  Returns TRUE if term1 and term2 are the same RDF term as defined in
  Resource Description Framework (RDF): Concepts and Abstract Syntax
  [CONCEPTS];
+ returns FALSE if the arguments are different types but both are
+ listed in §17.1 Operand Data Types;
  produces a type error if the arguments are both literal but are not
  the same RDF term *;
  returns FALSE otherwise. term1 and term2 are the same if any of the
  following is true:
  
      * term1 and term2 are equivalent IRIs as defined in 6.4 RDF URI
        References of [CONCEPTS].
  
      * term1 and term2 are equivalent literals as defined in 6.5.1
        Literal Equality of [CONCEPTS].
  
      * term1 and term2 are the same blank node as described in 6.6
        Blank Nodes of [CONCEPTS].
]]

[[
  * Invoking RDFterm-equal on two typed literals tests for equivalent
    values. An extended implementation may have support for additional
    datatypes. An implementation processing a query that tests for
    equivalence on unsupported datatypes
-   (and non-identical lexical form and datatype IRI)
    returns an error, indicating that it was unable to
    determine whether or not the values are equivalent. For example, an
    unextended implementation will produce an error when testing either
  
            "iiii"^^my:romanNumeral = "iv"^^my:romanNumeral or
            "iiii"^^my:romanNumeral != "iv"^^my:romanNumeral.
]]

> Andy's remark about "disjoint value spaces" made me look at the
> definition again, and realizing that the footnote says: "Invoking
> RDFterm-equal on two typed literals tests for equivalent values". I
> took this to mean that in my example case, I should not have simply
> returned a type error after the failed literal equality check, but
> should have done a lexical-to-value mapping, checking that both are
> semantically wellformed literals (which they are), and then just
> return FALSE for RDFterm-equals. This would result in
> "foo"^^xsd:string != "4"^^xsd:integer evaluating to TRUE. Which is
> what I would want it to be.
> 
> So, which is the correct interpretation? Or where am I going wrong?
> 
> Regards,
> 
> Jeen

-- 
-ericP

Received on Saturday, 26 March 2011 22:57:43 UTC