How to count sum of three columns MySql - mysql

I have three columns with names:
projectNo| process | procLeader | procCheker | Stuff |
----------+---------+------------+-------------+---------------+
16090001 | ANM | ben | barry | bob, bart, bok|
16090001 | BLD | anton | kirill | kart, ali |
What I want to is to count procLeader, procChecker, stuff columns assigned to projectNo. I managed to count each column by using query:
SELECT
COUNT(procLeader) AS `ld`,
COUNT(procChecker) AS `ch`,
SUM((LENGTH(stuff) - LENGTH(REPLACE(stuff,",","")) + 1)) AS `st`
FROM `process`
WHERE projectNo=16090001;
I get
ld| ch | st |
---+----+----+
2| 2| 5|
I need something like 'total' table
How I can sum this values? or maybe use another method?

SELECT
COUNT(procLeader) AS `ld`, COUNT(procCheker) AS `ch`,
SUM((LENGTH(stuff) - LENGTH(REPLACE(stuff,",","")) + 1)) AS `st` ,
(
COUNT(procLeader) +
COUNT(procCheker) +
SUM((LENGTH(stuff) - LENGTH(REPLACE(stuff,",","")) + 1))
) As `Total`
FROM `process` WHERE projectNo=16090001
Please let us know if you have any concerns or que.

Use the following query and it worked:
SELECT
COUNT(procLeader) AS `ld`, COUNT(procChecker) AS `ch`,
SUM((LENGTH(stuff) - LENGTH(REPLACE(stuff,",","")) + 1)) AS `st` ,
(
COUNT(procLeader) +
COUNT(procChecker) +
SUM((LENGTH(stuff) - LENGTH(REPLACE(stuff,",","")) + 1))
) As `Total`
FROM `process` WHERE projectNo = 16090001
Output:
Id - ch - st - Total
2 - 2 - 5 - 9

not sure I understand question, but if you want to count characters, did you try char_length and concat ?
SELECT char_length(concat(procleader, proccheker, REPLACE(stuff,',',''))) FROM process WHERE projectNo=16090001

Related

How to divide the same COUNT when there is a different WHERE statements?

I have no Idea how to google this stuff so i hope someone can help.
Table: PlayerMoves
HandNr | PlayerName | move | amount | OrderOfExecution
---+----------------+------+--------+-----------------
1 | Hans |raises|
1 | Hans |raises|
1 | Peter |raises|
1 | Hans |raises|
1 | Peter |folds |
Table: PlayersInTheHand
HandNr | Betround
-------+------------
1 | Preflop
SELECT STATEMENT1
Select playermoves.PlayerName,Count(playermoves.move)
FROM playersinthehand,playermoves
WHERE playersinthehand.Betround= 'Preflop' and
playersinthehand.handnr = playermoves.Nr
GROUP BY playermoves.PlayerName;
SELECT RESULT
PlayerName| Betround
-------+------------
Hans | 3
Peter | 2
SELECT STATEMENT2
Select playermoves.PlayerName,Count(playermoves.move)
FROM playersinthehand,playermoves
WHERE playersinthehand.Betround= 'Preflop' AND
playermoves.move = 'raises' or playermoves.move = 'calls'
or playermoves.move = 'bets' and
playersinthehand.handnr = playermoves.Nr
GROUP BY playermoves.PlayerName;
SELECT RESULT
PlayerName| Betround
-------+------------
Hans | 3
Peter | 1
My expected Results should be (Count from Statement 2 divided by Count from Statement 1) *100
EXPECTED RESULT
PlayerName| Betround
-------+------------
Hans | (3/3)*100 = 100%
Peter | (1/2)*100 = 50%
You can do conditional counting using SUM(CASE WHEN <predicate> THEN 1 ELSE 0 END).
For example:
SELECT
playermoves.PlayerName,
100.0 *
sum(case when playersinthehand.Betround = 'Preflop' AND
playermoves.move = 'raises' or playermoves.move = 'calls' then 1 else 0 end
) /
count(playermoves.move) as betround
FROM playersinthehand
join playermoves on playersinthehand.handnr = playermoves.Nr
WHERE playersinthehand.Betround= 'Preflop'
GROUP BY playermoves.PlayerName;
Result:
PlayerName betround
----------- ---------
Hans 100.00000
Peter 50.00000
See running example at DB Fiddle.
Try this. Maybe worth checking if you really need a join or just an 'exists'.
-- Auxiliary data for testing purposes
with PlayerMoves (handnr, playername, move) as(
select 1, 'Hans','raises'from dual union all
select 1, 'Hans','raises' from dual union all
select 1, 'Peter','raises' from dual union all
select 1, 'Hans','raises' from dual union all
select 1, 'Peter','folds' from dual),
PlayersInTheHand (handnr, betround) as(
select 1, 'Preflop ' from dual)
--Actual query
SELECT
playername,
round(SUM(
CASE
WHEN move = 'raises' THEN
1
END
) / COUNT(1) * 100, 2) betround
FROM
playermoves pm
WHERE
EXISTS (
SELECT
null
FROM
playersinthehand ph
WHERE
ph.handnr = pm.handnr
AND ph.betround = 'Preflop'
)
GROUP BY
playername;

MySQL query aggregate MAX and subquery

Is there a way to get value from a subquery in where inside select?
stop_link Table
id | duid | domain_id
1 | 1 | 1
2 | 2 | 1
3 | 1 | 2
4 | 2 | 2
5 | 3 | 1
Result that I want (assume domain_id = 2)
duid | domain_id
3 | 2
Query (not working):
INSERT INTO stop_link (
duid,
domain_id)
SELECT
IFNULL(MAX(sl.duid), 0) + 1 AS duid,
sl.domain_id
FROM
stop_link sl
WHERE sl.domain_id = (SELECT sd.id FROM stop_domain sd LIMIT 1)
Query working but I wish to avoid the Set Variable:
SET #domain_id = (SELECT sd.id FROM stop_domain sd LIMIT 1);
SELECT
IFNULL(MAX(sl.duid), 0) + 1 AS duid
, #domain_id
FROM
stop_link sl
WHERE sl.domain_id = #domain_id;
Do you mean something like this:
/*Your example Table*/
DECLARE #T
TABLE(ID INT,duid INT,domain_id INT)
INSERT INTO #T
VALUES
(1 , 1 , 1 ),
(2 , 2 , 1),
(3 , 1 , 2),
(4 , 2 , 2),
(5 , 3 , 1)
--The query
SELECT domain_id,Isnull(max(duid),0)+1 [newId]
FROM #T
GROUP BY domain_id
No need of max():
SELECT
IFNULL(sl.duid, 0) + 1 AS duid,
sl.domain_id
FROM
stop_link sl
WHERE sl.domain_id = (SELECT sd.id FROM stop_domain sd LIMIT 1)
ORDER by sl.id DESC
LIMIT 1
Changed answer based on new info from the comments. It sounds like you've got only_full_group_by enabled in your sql_mode. Your query would probably work with that disabled, but the following may also work for you:
INSERT INTO stop_link (
duid,
domain_id)
SELECT
IFNULL(MAX(sl.duid), 0) + 1 AS duid,
sl.domain_id
FROM
stop_link sl
WHERE sl.domain_id = (SELECT sd.id FROM stop_domain sd LIMIT 1)
-- ORDER by sl.domain_id DESC LIMIT 1 # Removed in favor of the following line
GROUP BY sl.domain_id HAVING MAX(sl.id)
;
Note that the subquery may not be returning the stop_domain.id that you want it to be -- you might have intended to select MAX(sd.id), or perhaps you just removed a WHERE sd.url='foo' for clarity's sake.

Comma Separated values into rows in mysql

SELECT DISTINCT jp.skills
FROM job_profile jp
UNION
SELECT js.skills
FROM job_seeker_profile js
The result:
|skills |
|php |
|PHP,Jquery,MVC |
|java |
|.net |
|Tally |
|php, mysql, yii |
|css, html, bootstrap|
|javascript, json |
but I need this as each item as row (each comma separated values as rows)
Expected result:
|skills |
|yii |
|PHP |
|Jquery |
|MVC |
|.net |
|Tally |
|bootstrap|
|css |
|html |
Create a split function which will split the data on , then create row wise data
SELECT distinct Split.fn.value('.', 'VARCHAR(100)') AS skills
FROM
(SELECT CAST ('<a>' + REPLACE(skills, ',', '</a><a>') + '</a>' AS XML) AS Data
FROM job_profile
) AS A CROSS APPLY Data.nodes ('/a') AS Split(fn);
Note: Update the inner query according to your need
Updated : In your case query will be
SELECT distinct Split.fn.value('.', 'VARCHAR(100)') AS skills
FROM
(SELECT CAST ('<a>' + REPLACE(jp.skills, ',', '</a><a>') + '</a>' AS XML) AS Data
FROM job_profile jp
UNION
SELECT js.skills
FROM job_seeker_profile js
) AS A CROSS APPLY Data.nodes ('/a') AS Split(fn);

How to GROUP BY a Subquery value returned by a CASE statement

I have been battling to find an answer for this. It is code that I maintain and has no errors. It is inside a stored procedure that returns data for a report.
I have made it smaller for readability and just included the essential parts.
It works with no error but a request has been made to make it group all related data in the respective rows.
Main issue is applying the GROUP BY statement for the third CASE statement which contains a SUBQUERY:
SELECT
CompanyName,
CompanyRef,
Amount,
Reference,
VendorNo,
CASE ErrorID WHEN 10 'Company Name: ' + CompanyName + 'CompanyRef' END AS InvalidCompanyNameForRef,
CASE ErrorID WHEN 11 'Vendor Number:' + VendorNo END AS InvalidVendorNo,
CASE ErrorID WHEN 12 (SELECT TOP(1) 'Non VAT Amount:' + CAST(PendingPayments.NonVatAmount AS varchar) + 'Import Amount:' + CAST(Imported.PaymentAmount) FROM PendingPayments
WHERE Imported.CompanyRef = PendingPayments.CompanyRef
AND Imported.VendorNo = PendingPayments.VendorNo
AND ISNUMERIC(Imported.PaymentAmount) = 1
AND CAST(Imported.PaymentAmount AS MONEY) <> PendingPayments.NonVatAmount AND PendingPayments.isVAT = 0
) END As PaymentAmountMismatch
.
.
.
GROUP BY
CompanyName,
CompanyRef,
Amount,
Reference,
VendorNo,
CASE ErrorID WHEN 10 'Company Name: ' + CompanyName + 'CompanyRef' END,
CASE ErrorID WHEN 11 'Vendor Number:' + VendorNo END
How do I make it group by the field derived from the SUBQUERY.
Instead of returning different rows for different columns of the same data, I would like it to return something like this:
CompanyName | CompanyRef | Amount | Reference | VendorNo | InvalidCompanyNameForRef | Invalid Vendor Number | PaymentAmountMismatch
------------+------------+--------+-----------+----------+------------------------------+-----------------------+-----------------------------------------+
ABC | 1 | 25.00 | INV001 |390 |Company Name: ABC CompanyRef:1| |
DEF | 5 | 12.00 | INV002 |212 | | 212 |Expected Amount:12.50, Import Amount:12.00
HIJ | 7 | 9.50 | INV003 |31 |Company Name: HIJ CompanyRef:7| |
It seems to me, CTE can help you. Code do not tested, but I think it's enough to get idea.
WITH cte
(CompanyName,
CompanyRef,
Amount,
Reference,
VendorNo,
InvalidCompanyNameForRef,
InvalidVendorNo,
PaymentAmountMismatch) AS
(
SELECT
CompanyName,
CompanyRef,
Amount,
Reference,
VendorNo,
CASE ErrorID WHEN 10 'Company Name: ' + CompanyName + 'CompanyRef' END AS InvalidCompanyNameForRef,
CASE ErrorID WHEN 11 'Vendor Number:' + VendorNo END AS InvalidVendorNo,
CASE ErrorID WHEN 12 (SELECT TOP(1) 'Non VAT Amount:' + CAST(PendingPayments.NonVatAmount AS varchar) + 'Import Amount:' + CAST(Imported.PaymentAmount) FROM PendingPayments
WHERE Imported.CompanyRef = PendingPayments.CompanyRef
AND Imported.VendorNo = PendingPayments.VendorNo
AND ISNUMERIC(Imported.PaymentAmount) = 1
AND CAST(Imported.PaymentAmount AS MONEY) <> PendingPayments.NonVatAmount AND PendingPayments.isVAT = 0
) END As PaymentAmountMismatch
)
SELECT * FROM cte
GROUP BY
CompanyName,
CompanyRef,
Amount,
Reference,
VendorNo,
InvalidCompanyNameForRef,
InvalidVendorNo,
PaymentAmountMismatch

Can I sum a calculation between two columns in Mysql?

What I would like to do is the following:
SELECT SUM(ABS(`number_x` - `number_y`)) AS `total_difference` FROM `table`
Where the table is as follow:
id | number_x | number_y
1 | 4 | 2
2 | 3 | 2
3 | 2 | 4
So the answer should be:
(4 - 2 = 2) + (3 - 2 = 1) + (2 - 4 = 2) = 5
Can I do this in MySQL and how?
Thanks!
The query you posted should work with no problem:
SELECT SUM(ABS(`number_x` - `number_y`)) AS `total_difference`
FROM `table`
Or if you want to write it with a subquery like so:
SELECT SUM(diff) AS `total_difference`
FROM
(
SELECT Id, ABS(number_x - number_y) diff
FROM TableName
) t
SELECT SUM(ABS(`number_x` - `number_y`)) AS `total_difference` FROM `table`
OR You can write other way, but i'll prefer above only
SELECT ABS(SUM(number_x) - SUM(number_y)) AS total_difference FROM table