Reputation: 1471
I have a table that I want to group by a binary variable group_generator
that defines end of the group: if it equals 1
, then the group contains all previous rows with group_generator = 0
Example:
Numbers group_generator
10 0
20 0
30 1
40 0
50 1
60 1
I need Numbers grouped in three groups:
(10, 20, 30);
(40, 50);
(60)
I tried creating a new column with sum of group_generator
for all rows with index less than current, like this:
Numbers group_generator group
10 0 0
20 0 0
30 1 0
40 0 1
50 1 1
60 1 2
and group by the last column, but that's complicated without temporary tables.
Is there an easy way do this in MySQL?
Upvotes: 0
Views: 685
Reputation: 147206
Once you have your new column, this query will give you the desired result:
SELECT GROUP_CONCAT(Numbers) FROM table GROUP BY `group`
Output:
group_concat(numbers)
10,20,30
40,50
60
So the whole query could be:
SELECT GROUP_CONCAT(Numbers),
(SELECT IFNULL(SUM(group_generator), 0) FROM table1 t2 WHERE t2.id < table1.id) AS `group`
FROM table1
GROUP BY `group`
Output
group_concat(Numbers) group
10,20,30 0
40,50 1
60 2
You could also produce this output with a stored procedure:
DELIMITER //
drop PROCEDURE if EXISTS groupit
//
create procedure groupit()
begin
declare num int;
declare numgroup varchar(1024) default '';
declare gnum int default 0;
declare pid int default 1;
declare gg int;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET gg = -1;
repeat
select group_generator, Numbers into gg, num from table2 where id=pid;
if (gg >= 0) then
set numgroup = concat(numgroup, if(numgroup='', '', ','), num);
if (gg = 1) then
select numgroup, gnum;
set numgroup = '';
set gnum = gnum + 1;
end if;
end if;
set pid=pid+1;
until gg = -1
end repeat;
end
//
delimiter ;
Upvotes: 1