Reputation: 21
I'm reasonably new to writing MySQL stored procedures, and I'm trying to get my head around using loops and variables.
I have a table with a column called STAT_NAME, where several rows could have the same value for that column. I want to create a temporary column which numbers the occurrences of each STAT_NAME value, so for example first time STAT_NAME is "stat A", set STAT_COUNT to 1, 2nd time 2 etc. And then start again at 1 for "stat B" and so on.
I've got as far as creating the the temporary table with an empty column called STAT_COUNT, and sorted the table by STAT_NAME.
I've then tried to loop through all the rows and set STAT_COUNT accordingly. However, I get the following error:
Error Code: 1064. You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '@counting,1) THEN SET @STAT_NAME_CURR = (SELECT @STAT_NAME FROM tmp1 LIMIT @'
Is anyone able to explain why what I've written is not OK? I think it would be fine if I used a system variable instead of @counting, and I don't understand why. I've tried googling the problem but not getting anywhere!
cheers.
DROP PROCEDURE IF EXISTS collate_stats;
delimiter //
CREATE PROCEDURE collate_stats()
begin
create temporary table tmp1 engine=memory
SELECT STAT_NAME, STAT, '' AS STAT_COUNT
FROM performance_testing_stats.20131014
ORDER BY STAT_NAME;
-- stat name that we are currently looking at
SET @STAT_NAME_CURR := "";
-- number of times this name has been found so far
SET @STAT_NAME_COUNT := 0;
-- Use to loop through all rows
SET @n := (SELECT COUNT(*) FROM tmp1);
-- Row reached so far
SET @counting := 0;
WHILE @counting < @n DO
-- IF @STAT_NAME_CURR is not equal to the STAT_NAME for the current row,
-- THEN set @STAT_NAME_CURR to STAT_NAME value and reset @STAT_NAME_COUNT
-- ELSE just increment @STAT_NAME_COUNT
IF @STAT_NAME_CURR <> (SELECT @STAT_NAME FROM tmp1 LIMIT @counting,1) THEN
SET @STAT_NAME_CURR = (SELECT @STAT_NAME FROM tmp1 LIMIT @counting,1);
SET @STAT_NAME_COUNT = 0;
ELSE
SET @STAT_NAME_COUNT = @STAT_NAME_COUNT + 1;
END IF;
-- Set STAT_COUNT for current row to value of @STAT_NAME_COUNT
UPDATE tmp1 SET STAT_COUNT = @STAT_NAME_COUNT WHERE STAT_NAME = @STAT_NAME_CURR AND STAT_COUNT = '' LIMIT 1;
-- Move to next row
SET @counting = @counting + 1;
END WHILE;
select * from tmp1;
END //
delimiter ;
Upvotes: 2
Views: 504
Reputation: 17610
You might want to look into using cursors instead of the while loop.
However, you could probably accomplish what you are trying to do with a simple GROUP BY query:
SELECT STAT_NAME, STAT, COUNT(1) as STAT_COUNT
FROM performance_testing_stats.20131014
GROUP BY STAT_NAME, STAT
ORDER BY STAT_NAME, STAT;
Unless I'm missing something about what you are doing.
Upvotes: 1