question on sparql 1.1 test 'Protect from error in AVG'

The test uses:

==> agg-err-02.ttl <==
@prefix : <http://example.com/data/#> .

:x :p 1, "2", 3, 4 .
:y :p 1, _:b2, 3, 4 .
:z :p 2.5e0, "not a double" , 3.5, 4 .

==> agg-err-02.rq <==
PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX : <http://example.com/data/#>
SELECT ?g
(AVG(IF(isNumeric(?p), ?p, COALESCE(xsd:double(?p),0))) AS ?avg)
WHERE {
  ?g :p ?p .
}
GROUP BY ?g


Lets work this through


First grouping by subject and I added the XSD types in []s

x group:
1 [integer], "2" [string], 3 [integer], 4 [integer]

y group:
1 [integer], _:b2 [bnode], 3 [integer], 4 [integer]

z group:
2.5e0 [double], "not a double", 3.5 [decimal], 4 [integer]

so now evaluate the isNumeric.  The second values are
replaced by xsd:double(?p) or 0 [integer] if that fails


x group:
1 [integer], 2.0E0 [double], 3 [integer], 4 [integer]

y group:
1 [integer], 0 [integer], 3 [integer], 4 [integer]

z group:
2.5e0 [double], 0 [integer], 3.5 [decimal], 4 [integer]


Now the averages, type promoting based on the + operator then / operator

x group:
( 1 [integer] + 2.0E0 [double] + 3 [integer] + 4 [integer] ) / 4 [integer]
= 10E0 [double] / 4 [integer]
= 2.5E0 [double]

y group:
( 1 [integer], 0 [integer], 3 [integer], 4 [integer] ) / 4 [integer]
= 10 [integer] / 4 [integer]
  and by XSD  int/int division rule the result is always decimal
= 2.5 [decimal]

z group:
( 2.5e0 [double], 0 [integer], 3.5 [decimal], 4 [integer] ) / 4 [integer]
= 10.0 [ decimal ] / 4 [integer]
= 2.5 [decimal]

Results:
g avg
-----
x 2.5E0 [double]
y 2.0 [decimal]
z 2.5 [decimal]

Expected results:
g avg
-----
x 2.5e0 [double]
y 2.0 [decimal]
z 2.5E0 [double]

The z result doesn't match the types but they are equal values - is that
good enough or did I go wrong somewhere?

Are there different type conversion rules for AVG and aggregate ops?

Dave

Received on Saturday, 24 March 2012 04:35:44 UTC