De logaritme/kracht-benadering is de algemeen gebruikte benadering. Voor Oracle is dat:
select exp(sum(ln(col)))
from table;
Ik weet niet waarom de oorspronkelijke databaseontwerpers PRODUCT()
niet hebben opgenomen als aggregatiefunctie. Mijn beste gok is dat het allemaal computerwetenschappers waren, zonder statistici. Dergelijke functies zijn erg handig in statistieken, maar komen niet veel voor in de informatica. Misschien wilden ze niet omgaan met overloopproblemen die zo'n functie zou impliceren (vooral bij gehele getallen).
Trouwens, deze functie ontbreekt in de meeste databases, zelfs die welke veel statistische aggregatiefuncties implementeren.
bewerken:
Oy, het probleem van negatieve getallen maakt het een beetje ingewikkelder:
select ((case when mod(sum(sign(col)), 2) = 0 then 1 else -1 end) *
exp(sum(ln(abs(col))))
) as product
Ik ben niet zeker van een veilige manier in Oracle om 0
te verwerken s. Dit is een "logische" benadering:
select (case when sum(case when col = 0 then 1 else 0 end) > 0
then NULL
when mod(sum(sign(col)), 2) = 0
then exp(sum(ln(abs(col)))
else - exp(sum(ln(abs(col)))
end)
) as product
Het probleem is dat de database-engine een fout in het logboek kan krijgen voordat de case
. wordt uitgevoerd uitspraak. Dat is toevallig hoe SQL Server werkt. Ik ben niet zeker van Oracle.
Ah, dit zou kunnen werken:
select (case when sum(case when col = 0 then 1 else 0 end) > 0
then NULL
when mod(sum(sign(col)), 2) = 0
then exp(sum(ln(case when col <> 0 then abs(col) end)))
else - exp(sum(ln(case when col <> 0 then abs(col) end)))
end)
) as product
Het retourneert NULL
wanneer er een 0
. is .