WITH tbl AS
(SELECT 2 num
FROM DUAL
UNION
SELECT 3 num
FROM DUAL
UNION
SELECT 4 num
FROM DUAL)
SELECT num
FROM tbl;
Code language: SQL (Structured Query Language) (sql)
We need the multiplication of row’s data for this column. So essentially, we are looking for an aggregate function MUL (num). There is no such function as MUL () in Oracle (I actually tried using it). Here comes the computational part of the puzzle. A multiplication operation can be mathematically expressed as: MUL (num) = EXP (SUM (LN (num))) Not very clear at first, I agree. Lets review the maths behind it: x = (2 * 3 * 4) ln(x) = ln(2 * 3 * 4) ln(x) = ln(2) + ln(3) + ln(4) => SUM(LN(num)) ln(x) = .693 + 1.098 + 1.386 ln(x) = 3.178 x = e (3.178) => EXP(SUM(LN(num))) x = 24 And that’s it. We just created our own multiplication function and now the result can be calculated as: WITH tbl AS
(SELECT 2 num
FROM DUAL
UNION
SELECT 3 num
FROM DUAL
UNION
SELECT 4 num
FROM DUAL)
SELECT EXP (SUM (LN (num))) MUL
FROM tbl;
Code language: SQL (Structured Query Language) (sql)
Result: 24 Everything looks perfect. But hey, I have got negative values. The moment you put a negative value in the dataset, you are bound to get the following Oracle error: “ORA-01428: argument ‘x’ is out of range” This is because the range for LN () argument is > 0. But this is now easy to handle, here is how: WITH tbl AS
(SELECT -2 num
FROM DUAL
UNION
SELECT -3 num
FROM DUAL
UNION
SELECT -4 num
FROM DUAL),
sign_val AS
(SELECT CASE MOD (COUNT (*), 2)
WHEN 0 THEN 1
ELSE -1
END val
FROM tbl
WHERE num < 0)
SELECT EXP (SUM (LN (ABS (num)))) * val
FROM tbl, sign_val
GROUP BY val
Code language: SQL (Structured Query Language) (sql)
Result: -24 So, we first counted the negative records in the table. If the count is odd, the final result should be negative and vice versa. We then multiplied this signed value with the multiplication of the absolute values. A subquery can also be used instead of GROUP BY but that’s trivial. Now the solution is complete and we are able to handle the negative values too. I was so impressed by this approach that I haven’t given a thought about any other solution. But I am sure there would be. If you find a different approach, please share. Java URL Encoder/Decoder Example - In this tutorial we will see how to URL encode/decode…
Show Multiple Examples in OpenAPI - OpenAPI (aka Swagger) Specifications has become a defecto standard…
Local WordPress using Docker - Running a local WordPress development environment is crucial for testing…
1. JWT Token Overview JSON Web Token (JWT) is an open standard defines a compact…
GraphQL Subscription provides a great way of building real-time API. In this tutorial we will…
1. Overview Spring Boot Webflux DynamoDB Integration tests - In this tutorial we will see…
View Comments
Wow! Very simple!
Very Good Example. Did not think it was so easy
It`s not work if any num=0
SET SERVEROUTPUT ON;
DECLARE
v_str VARCHAR2(100);
v_num NUMBER;
BEGIN
WITH tbl AS
(SELECT 2 num
FROM DUAL
UNION
SELECT 3 num
FROM DUAL
UNION
SELECT 4 num
FROM DUAL)
SELECT LISTAGG(num, '*') WITHIN GROUP (ORDER BY num) INTO v_str
FROM tbl;
EXECUTE IMMEDIATE 'SELECT ' ||v_str||' FROM dual' INTO v_num;
DBMS_OUTPUT.PUT_LINE (v_str || ' = '|| v_num);
END;
SET SERVEROUTPUT ON;
DECLARE
v_str VARCHAR2(100);
v_num NUMBER;
BEGIN
WITH tbl AS
(SELECT 2 num
FROM DUAL
UNION
SELECT 3 num
FROM DUAL
UNION
SELECT 4 num
FROM DUAL)
SELECT LISTAGG(num, '*') WITHIN GROUP (ORDER BY num) INTO v_str
FROM tbl;
EXECUTE IMMEDIATE 'SELECT ' ||v_str||' FROM dual' INTO v_num;
DBMS_OUTPUT.PUT_LINE (v_str || ' = '|| v_num);
END;
good article