2

I have below 2 tables and I have to, write a query to display the sum of the total amount received through the credit card and cheque. Give the alias names as 'total_credit' and 'total_cheque' respectively.

table_payment
id (PK)
user_id
amount
transaction_type_id (FK)

table_transaction_type
id (PK)
type

Expected Output:

total_credit| total_cheque     
Value a     | Value B

I tried with below query but I getting values in different rows

select  sum(case when tt.type = 'Credit Card' then pt.amount end) as
"total_credit",  sum (case when tt.type = 'Cheque' then pt.amount end)
as "total_cheque" from payment pt join transaction_type tt on
pt.transaction_type_id = tt.id group by tt.type

Actual_Output:

total_credit| total_cheque     
Value A     |     
            | Value B

not sure how to get Value B in first row along with Value A, please advice.

0

6 Answers 6

2

What you're looking to do is "pivot" the data, and Oracle provides a pivoting function:

WITH 
   T 
AS 
(
   select tt.type, pt.amount
     from payment pt
     join transaction_type tt on tt.id = pt.transaction_type_id
)
SELECT 
   *
FROM 
   T
PIVOT 
(
   SUM(amount) 
   FOR 
      (type) 
   IN 
      ('Credit Card', 'Cheque')
);

Further examples can be found here: http://www.dba-oracle.com/t_pivot_examples.htm

Sign up to request clarification or add additional context in comments.

Comments

1
select user_id, sum(case when tt.type='Credit Card' the amount end) as total_credit, sum(case when tt.type='Cheque' the amount end) as total_credit 
from table_payment p
inner join table_transaction_type tt
on p.transaction_type_id = tt.id
group by user_id;

1 Comment

It looks like you decided to change the table names (table_cheque isn't a table in his original question.)
0
select  (SELECT sum(pt.amount FROM from payment pt 
join transaction_type tt on pt.transaction_type_id = tt.id 
WHERE tt.type = 'Credit Card'
group by tt.type) as "total_credit"
, (SELECT sum(pt.amount FROM from payment pt 
join transaction_type tt on pt.transaction_type_id = tt.id 
WHERE tt.type = 'Cheque'
group by tt.type) as "total_cheque"

I considered using it as two sub queries, but it looks like we're not joining on any other ID or anything.

Full disclosure: I'm not familiar with Oracle, but this query will definitely work in T-SQL, and I believe it would work in MySQL, so I don't see why it wouldn't work in Oracle, too.

Comments

0

can't you just add a max to it?

  SELECT MAX (SUM (CASE WHEN tt.TYPE = 'Credit Card' THEN pt.amount END))
             AS "total_credit",
         MAX (SUM (CASE WHEN tt.TYPE = 'Cheque' THEN pt.amount END))
             AS "total_cheque"
    FROM payment pt JOIN transaction_type tt ON pt.transaction_type_id = tt.id
GROUP BY tt.TYPE

here is a sample with fake data you can run in oracle.

WITH
    transaction_type
    AS
        (SELECT 1 id, 'Credit Card' AS TYPE FROM DUAL
         UNION ALL
         SELECT 2, 'Cheque' FROM DUAL),
    payment
    AS
        (SELECT 500 AS amount, 1 AS transaction_type_id FROM DUAL
         UNION ALL
         SELECT 300, 2 FROM DUAL
         UNION ALL
         SELECT 200, 1 FROM DUAL
         UNION ALL
         SELECT 400, 2 FROM DUAL)
  SELECT MAX (SUM (CASE WHEN tt.TYPE = 'Credit Card' THEN pt.amount END))
             AS "total_credit",
         MAX (SUM (CASE WHEN tt.TYPE = 'Cheque' THEN pt.amount END))
             AS "total_cheque"
    FROM payment pt JOIN transaction_type tt ON pt.transaction_type_id = tt.id
GROUP BY tt.TYPE

result

 total_credit total_cheque
 700          700

2 Comments

Far too complicated! Just drop the GROUP BY clause in the original query - that's all that is needed.
I thougt SUM whas what was required not MAX ?!
0

don't group by tt.type - that is why you get that result. If you need to group by user_id (as in one of the solutions) then do; if you need a result with exactly one row and two columns, aggregated (summed) over all users, don't group by ANYTHING, you don't need a GROUP BY clause. (I believe the SQL Standard doesn't allow that; Oracle definitely does, but if that bothers you, you can add something trivial, like GROUP BY NULL.)

Comments

0

Simply use the code without group by clause

select  sum(case when tt.type = 'Credit Card' then pt.amount end) as
total_credit,  sum (case when tt.type = 'Cheque' then pt.amount end)
as total_cheque from payment pt join transaction_type tt on
pt.transaction_type_id = tt.id

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.