I have two table insert1 and received1
in insert1 table have column and column name is recharge_account.
received table have one column and column name is received_amount.
I want to total recharge_ammount - total received_amount as dues.
recharge_Account Received_Amount dues
500 - 400 100
SELECT
SUM(Account_recharge) AS `Total Recharge`,
SUM(Amount_Received) AS `Total Received`,
SUM(Account_recharge) - SUM(Amount_Received) AS dues
FROM insert1 i1
INNER JOIN received1 r1
i am not get to exact calculation .
You just need a join condition such as ON i1.id = r1.ins_id, and COALESCE() function against null values :
SELECT
SUM(COALESCE(Account_recharge,0)) AS `Total Recharge`,
SUM(COALESCE(Amount_Received,0)) AS `Total Received`,
SUM(COALESCE(Account_recharge,0)) - SUM(COALESCE(Amount_Received,0)) AS dues
FROM insert1 i1
JOIN received1 r1 ON i1.id = r1.ins_id
I would recommend union all and group by:
SELECT SUM(ir.Account_recharge) AS `Total Recharge`,
SUM(ir.Amount_Received) AS `Total Received`,
SUM(ir.Account_recharge) - SUM(ir.Amount_Received) AS dues
FROM ((SELECT Account_recharge, NULL as Amount_Received
FROM insert1 i1
) UNION ALL
(SELECT NULL as Account_recharge, Amount_Received
FROM received1 r1
)
) ir
Actually, a CROSS JOIN also works:
SELECT SUM(i.Account_recharge) AS `Total Recharge`,
SUM(r.Amount_Received) AS `Total Received`,
SUM(i.Account_recharge) - SUM(r.Amount_Received) AS dues
FROM (SELECT SUM(Account_recharge) as Account_recharge
FROM insert1 i1
) i CROSS JOIN
(SELECT SUM(Amount_Received) as Amount_Received
FROM received1 r1
) r;
The key in this case is that you need to aggregate before joining.
As I understand you don't need any kind of join.
You can sum over each column and return the 2 total columns in a subquery to subtract them:
SELECT t.`Total Recharge`, t.`Total Received`,
t.`Total Recharge` - t.`Total Received` AS dues
FROM (
SELECT
(SELECT SUM(Account_recharge) FROM insert1) AS `Total Recharge`,
(SELECT SUM(Amount_Received) FROM received1) AS `Total Received`
) AS t
Related
I am working on this question and I appreciate for your help!
Question in detail
I will just paste here the query to create tables and add records in them. It might be easier to test.
CREATE TABLE user_financial_detail(
id INT PRIMARY KEY,
first_name varchar(20),
last_name varchar(20),
vpa VARCHAR(20),
credit_limit int
);
CREATE TABLE transaction_log(
id INT PRIMARY KEY,
paid_by VARCHAR(20),
paid_to VARCHAR(20),
amount INT,
transacted_on TIMESTAMP
);
INSERT INTO user_financial_detail VALUES
(1,'shea','caldwell','sc',5000),
(2,'martena','leblanc','ml',10000),
(3,'tashya','riley','tr',25000);
INSERT INTO transaction_log VALUES
(1,'ml','tr',13155,'2019/11/21'),
(2,'tr','ml',10883,'2019/09/10'),
(3,'sc','tr',15012,'2018/12/25'),
(4,'ml','sc',5700,'2018/05/18'),
(5,'tr','sc',18473,'2018/07/02');
Table layouts
First, find balance for each user:
select vpa, sum(total_amount) balance
from (
select paid_by vpa, sum(-amount) total_amount
from transaction_log
group by paid_by
union all
select paid_to vpa, sum(amount) total_amount
from transaction_log
group by paid_to
) b
group by vpa
Then join this result with user_financial_detail to get the rest of the data:
select
concat(u.first_name, ' ', u.last_name) name,
b.vpa,
b.balance + u.credit_limit current_balance,
case
when b.balance + u.credit_limit >= 0 then 'no'
else 'yes'
end credit_limit_breached
from user_financial_detail u
inner join (
select vpa, sum(total_amount) balance
from (
select paid_by vpa, sum(-amount) total_amount
from transaction_log
group by paid_by
union all
select paid_to vpa, sum(amount) total_amount
from transaction_log
group by paid_to
) bi
group by vpa
) b on b.vpa = u.vpa
Result:
name vpa current_balance credit_limit_breached
shea caldwell sc 14161 no
martena leblanc ml 2028 no
tashya riley tr 23811 no
Demo on DB Fiddle
SELECT Concat(u.first_name, ' ', u.last_name) NAME,
b.vpa,
b.current_balance,
CASE
WHEN b.current_balance < 0
AND Abs(b.current_balance) > u.credit_limit THEN "yes"
ELSE "no"
END credit_limit_breached
FROM user_financial_detail u
INNER JOIN (SELECT vpa,
Sum(total_amount) current_balance
FROM (SELECT paid_by vpa,
Sum(-amount) total_amount
FROM transaction_log
GROUP BY paid_by
UNION ALL
SELECT paid_to vpa,
Sum(amount) total_amount
FROM transaction_log
GROUP BY paid_to) bi
GROUP BY vpa) b
ON b.vpa = u.vpa;
with credit as (select a.vpa,sum(b.amount) as credit from user_financial_detail as a inner join transaction_log as b on a.vpa=b.paid_to group by a.vpa)
, debit as (select a.vpa,sum(b.amount) as debit from user_financial_detail as a inner join transaction_log as b on a.vpa=b.paid_by group by a.vpa)
select a.vpa,(b.credit-c.debit),case
when (b.credit-c.debit)<0 then 'yes'
else 'no'
end
from user_financial_detail as a inner join credit as b on a.vpa=b.vpa inner join debit as c on a.vpa=c.vpa;
I have tables that contain same field, for example:
p_central_ticket p_south_ticket p_west_ticket
=====================================================================
- t_id - t_id - t_id
- t_req_type - t_req_type - t_req_type
- t_status - t_status - t_status
And i have one table :
m_event_type
=============
- ev_type
- ev_activity
My current query :
SELECT ev_activity AS Activity, COUNT( * ) AS Total
FROM m_event_type
LEFT JOIN p_central_ticket ON p_central_ticket.t_req_type = m_event_type.ev_type
WHERE t_status =9
GROUP BY ev_activity
Output from query above:
My question is, how should i do, if i want to total count from 3 tables above.
(For Example Activity Change Request total 18000, count from
p_central_ticket + p_south_ticket + p_west_ticket) etc.
Thanks...
Use union all in a subquery, then join it:
select t1.ev_Activity, count(t1.*) as total
from m_event_type t1
LEFT JOIN
(
select *
from p_central_ticket
WHERE t_status =9
union all
select *
from p_south_ticket
WHERE t_status =9
union all
select *
from p_west_ticket
WHERE t_status =9
) t2
ON t2.t_req_type = t1.ev_type
GROUP BY t1.ev_activity
Use a UNION ALL (to avoid removing duplicates) then SUM the quantities
Note that it also works if your tables have different column names you only need to alias them in the select.
SELECT ev_activity AS Activity, SUM(quantity) AS Total
FROM m_event_type met
LEFT JOIN (SELECT c.t_req_type, COUNT(*) as quantity
FROM p_central_ticket c
WHERE c.t_status =9
GROUP BY c.t_req_type
UNION ALL
SELECT s.t_req_type, COUNT(*)
FROM p_south_ticket s
WHERE s.t_status =9
GROUP BY s.t_req_type
UNION ALL
SELECT w.t_req_type, COUNT(*)
FROM p_west_ticket w
WHERE w.t_status =9
GROUP BY w.t_req_type) p ON
p.t_req_type = met.ev_type
GROUP BY ev_activity
You could use UNION ALL for select all the rows of the 3 tables
SELECT ev_activity AS Activity, COUNT( * ) AS Total
FROM m_event_type
LEFT JOIN (
select t_id, t_req_type, t_status
from p_central_ticket
union all
select t_id, t_req_type, t_status
from p_south_ticket
union all
select t_id, t_req_type, t_status
from p_west_ticket
) t ON t.t_req_type = m_event_type.ev_type
WHERE t.t_status =9
GROUP BY ev_activity
Hi below is my sql query as
SELECT
o.OrderNumber,
oi.Sku,
Sum(Isnull(oi.Price * oi.Quantity,0)) as Price,
DENSE_RANK() over(partition by o.orderNumber order by oi.sku) as CouponRowId
from ac_OrderItems oi
inner join ac_Orders o on oi.OrderId = o.OrderId
Inner Join ac_OrderShipments os on oi.OrderShipmentId =os.OrderShipmentId
WHERE (oi.OrderItemTypeId IN (5))
group by o.OrderNumber, oi.Sku
and below is the record I am getting
OrderNumber Sku Price CouponRowId
90061 BLACKBERRY -5.6900 1
90061 LEMON -5.6900 2
90061 PEACH -5.6900 3
90061 SHIP100 -10.920 4
but I want my record as
OrderNumber Sku Price
90061 BLACKBERRY -5.6900
LEMON -5.6900
PEACH -5.6900
SHIP100 -10.920
I want that if order number is same in that case all detail record should come in 1st row and then after other record should only show Sku and price only and also we need to remove the DENSE_RANK() column
By seeing the query seems like Partition Clause can help you to
resolve the issue. Please look at the below query. I am not so sure
about the data model, but looks like you need to partition by using
the OrderNumber column. Please replace the query in the first CTE with your actual table which will be like the second query. I cant test it since I don't have the environment. Please test the query
;WITH CTE_Table
AS
(
SELECT 90061 'OrderNumber' , 'BLACKBERRY' Sku, -5.6900 'Price', 1 'CouponRowId' UNION
SELECT 90061, 'LEMON', -5.6900, 2 UNION
SELECT 90061, 'PEACH', -5.6900, 3 UNION
SELECT 90061, 'SHIP100', -10.920, 4 UNION
SELECT 90062 'OrderNumber' , 'BLACKBERRY' Sku, -5.6900 'Price', 1 'CouponRowId' UNION
SELECT 90062, 'LEMON', -5.6900, 2 UNION
SELECT 90062, 'PEACH', -5.6900, 3 UNION
SELECT 90062, 'SHIP100', -10.920, 4
),
CTE_New
AS
(
SELECT *, ROW_NUMBER() OVER(PARTITION BY OrderNumber ORDER BY OrderNumber) Patrn FROM CTE_Table
)
SELECT CASE WHEN Patrn =1 THEN CONVERT(VARCHAR(10),OrderNumber) ELSE '' END OrderNumber, Sku, Price, CouponRowId FROM CTE_New
;WITH CTE_Table
AS
(
SELECT
o.OrderNumber,
oi.Sku,
Sum(Isnull(oi.Price * oi.Quantity,0)) as Price,
DENSE_RANK() over(partition by o.orderNumber order by oi.sku) as CouponRowId
from ac_OrderItems oi
inner join ac_Orders o on oi.OrderId = o.OrderId
Inner Join ac_OrderShipments os on oi.OrderShipmentId =os.OrderShipmentId
WHERE (oi.OrderItemTypeId IN (5))
group by o.OrderNumber, oi.Sku
),
CTE_New
AS
(
SELECT *, ROW_NUMBER() OVER(PARTITION BY OrderNumber ORDER BY OrderNumber) Patrn FROM CTE_Table
)
SELECT CASE WHEN Patrn =1 THEN CONVERT(VARCHAR(10),OrderNumber) ELSE '' END OrderNumber, Sku, Price, CouponRowId FROM CTE_New
Seeing your comment this is an attempt to solve it on the query itself (I assumed CouponRowID might do the job, if OrderNumber is unique):
WITH
tmp AS (
SELECT o.OrderNumber, oi.Sku, SUM(ISNULL(oi.Price * oi.Quantity, 0)) AS Price, DENSE_RANK() OVER (PARTITION BY o.orderNumber ORDER BY oi.sku) AS CouponRowId
FROM ac_OrderItems oi
INNER JOIN ac_Orders o ON oi.OrderId=o.OrderId
INNER JOIN ac_OrderShipments os ON oi.OrderShipmentId=os.OrderShipmentId
WHERE(oi.OrderItemTypeId IN (5))
GROUP BY o.OrderNumber, oi.Sku
)
SELECT CASE WHEN tmp.CouponRowId=1 THEN tmp.OrderNumber END AS OrderNumber, tmp.Sku, tmp.Price
FROM tmp
ORDER BY tmp.OrderNumber, tmp.SKu;
Sorry....! I cant understand your explanations..
I just worked only for get your expected OP...
create table #ac_OrderItems(id varchar(20) --varchar, i used instead of int.Beside, varchar is easy to change to int.
, Sku varchar(20), Price decimal, CouponRowId int)
insert into #ac_OrderItems values(
90061 , 'BLACKBERRY' , -5.6900 , 1)
,(90061, 'LEMON', -5.6900, 2 )
,(90061, 'PEACH', -5.6900, 3 )
,(90061, 'SHIP100', -10.920, 4 )
,(90062 , 'BLACKBERRY' ,-5.6900 , 1 )
,(90062, 'LEMON', -5.6900, 2 )
,(90062, 'PEACH', -5.6900, 3 )
,(90062, 'SHIP100', -10.920, 4)
select * from #ac_OrderItems
;with
orders(id, sku, price, couponId, rn)
as
(
select *, ROW_NUMBER() over(partition by id order by id) from #ac_OrderItems
)select iif(rn = 1,id,''),sku,price,couponId from orders
-- if i used int, empty is denoted by 0. But you want '' this. So i used varchar id
let you know me, what you got.
I have the following query that is working perfectly right now, I have been trying to optimize it since I am using the same subquery 4 times. It will be great to come up with a better/smarter solution. Thank you
Here is the query:
select
invoices.invoice_id
,invoices.invoice_amount
,(
select SUM(invoice_payment_amount) as total
FROM invoice_payments
where invoice_payment_invoice_id = invoices.invoice_id
) as payments
,round((invoices.invoice_amount-(
select SUM(invoice_payment_amount) as total
FROM invoice_payments
where invoice_payment_invoice_id = invoices.invoice_id
)),2) as balance
from invoices
where (
round((invoices.invoice_amount -
(select SUM(invoice_payment_amount) as total
FROM invoice_payments
where invoice_payment_invoice_id = invoices.invoice_id)
),2)
) > 0
or (
round((invoices.invoice_amount -
(select SUM(invoice_payment_amount) as total
FROM invoice_payments
where invoice_payment_invoice_id = invoices.invoice_id)
),2)
) IS NULL
order by balance
SQL Fiddle: http://sqlfiddle.com/#!9/aecea/1
Just use a subquery:
select i.invoice_id, i.invoice_amount, i.payments,
round((i.invoice_amount- i.payments), 2) as balance
from (select i.*,
(select sum(ip.invoice_payment_amount)
from invoice_payments ip
where ip.invoice_payment_invoice_id = i.invoice_id
) as payments
from invoices i
) i
where round((i.invoice_amount- i.payments), 2) > 0 or
round((i.invoice_amount- i.payments), 2) is null
order by balance;
For better performance, you want an index on invoice_payments(invoice_payment_invoice_id, invoice_payment_amount).
I have two SELECT statements that give the values "TotalSales" and "VendorPay_Com". I want to be able to subtract VendorPay_Com from TotalSales within the one MySQL statement to get the value "Outstanding_Funds" but I haven't found a reliable way to do so.
These are my two statements:
Query 1:
SELECT SUM(Price) AS TotalSales
FROM PROPERTY
WHERE Status = 'Sold';
Query 2:
SELECT SUM(AC.Amount) AS VendorPay_Comm
FROM (
SELECT Amount FROM lawyer_pays_vendor
UNION ALL
SELECT CommissionEarned AS `Amount` FROM COMMISSION AS C WHERE C.`status` = 'Paid') AS AC
Any help on this matter would be greatly appreciated :)
You can do it as follows :
select (select ...) - (select ...)
In your example, simply :
select
(
SELECT SUM(Price) AS TotalSales
FROM PROPERTY
WHERE Status = 'Sold'
)
-
(
SELECT SUM(AC.Amount) AS VendorPay_Comm
FROM (
SELECT Amount FROM lawyer_pays_vendor
UNION ALL
SELECT CommissionEarned AS `Amount` FROM COMMISSION AS C WHERE C.`status` = 'Paid') AS AC
) AS Outstanding_Funds
Try
SELECT TotalSales-VendorPay_Comm AS Outstanding_Funds
FROM
(SELECT SUM(Price) AS TotalSales
FROM PROPERTY
WHERE Status = 'Sold') t1,
(SELECT SUM(Amount) AS VendorPay_Comm
FROM (SELECT Amount FROM lawyer_pays_vendor
UNION ALL
SELECT CommissionEarned AS Amount
FROM COMMISSION
WHERE Status = 'Paid') t0) t2
Here is sqlfiddle