Suppose i have a table which has heterogenous columns(varchar, int, etc).
+-------+----+----+----+
| Nme | Py | cm | Mt |
+-------+----+----+----+
| johny | 68 | 70 | 66 |
| Harry | 86 | 76 | 90 |
| johny | 18 | 72 | 66 |
+-------+----+----+----+
and in need to calulate sum of each integer column but using some generic sql query such that even if i am adding new integer columns, i won't have to change the query.
What i need but in a generic form
SELECT SUM(Py), SUM(cm), SUM(Mt) FROM table GROUP BY NME;
To something like:
SELECT SUM(*) FROM table WHERE <COLUMNTYPE(INT)> GROUP BY NME;
Is there a way around or it is not possible in SQL?
No such thing. You seem to misunderstand how to use SQL. I think you need a table that "unpivots" your data. Something like:
create table personValues (
personValues int auto_increment primary key,
person varchar(255),
value_type varchar(255),
value int
);
So, what is now one row would be three rows. You would then get the results in different rows, but you do get the results:
select value_type, sum(value)
from personValues
group by value_type;
If you then need to pivot this to single row, you have two options:
group_concat()
to create a long string. If you want to try dynamic sql for this?
Here's an example snippet for MySql:
-- Adding a test table
drop table if exists test_dynamic;
create table test_dynamic (ID int auto_increment primary key, Nme varchar(30), Py int, Cm int, Mt int);
-- Some sample data
insert into test_dynamic (Nme, Py, Cm, Mt) values
('johny',68,70,66),
('Harry',86,76,90),
('johny',18,72,66);
-- Build a string for the aggregations
set @Sums := (select group_concat(concat(' SUM(', column_name, ') as ', column_name)) as sums
from information_schema.columns
where table_schema = database()
and table_name = 'test_dynamic'
and data_type = 'int'
and column_key != 'PRI');
-- Stick it to a string for the select
set @DynSql := concat('select
Nme,
', @Sums, '
from test_dynamic
group by Nme
order by Nme');
-- Run the created dynamic sql string
PREPARE stmt FROM @DynSql;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;
Returns:
Nme Py Cm Mt
---- -- -- --
Harry 86 76 90
johny 86 142 132
No single sql statement can do this task.
BEGIN
DECLARE @ColumnSUM nvarchar(max) = 'NME'
SELECT @ColumnSUM += ', SUM(' + COLUMN_NAME + ') ' + COLUMN_NAME
FROM INFORMATION_SCHEMA.COLUMNS
WHERE TABLE_NAME = 'test_dynamic'
AND DATA_TYPE = 'int'
AND COLUMN_NAME != 'ID'
EXEC('SELECT ' + @ColumnSUM + ' FROM test_dynamic GROUP BY NME ORDER BY NME')
END
Result:
NME Py Cm Mt
--- -- -- --
Harry 86 76 90
johny 86 142 132
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.