【发布时间】:2015-11-29 22:33:40
【问题描述】:
我正在尝试使用新过程向工作表添加一列,该过程与我用来填充工作表中已有列的过程不同。我不确定这样做是否会更有效和节省资源,或者通过添加到我用来填充表中已经存在的列/值的原始过程。无论如何,这里是添加此列的单独过程的代码。该列称为“starter_rest”,表示为“Game_Date”字段中的日期值与该字段/列中先前值之间的差异。
这是我正在使用的代码,它给了我一个错误。
如果存在,则删除过程 accumulate_starter_rest()
分隔符 $$
CREATE PROCEDURE accumulate_starter_rest()
BEGIN
DECLARE pit_id VARCHAR(8);
DECLARE gdate DATE;
DECLARE prev_date DATE;
DECLARE seq INT;
DECLARE strt_rst REAL;
DECLARE prev_year YEAR(4);
DECLARE end_of_cursor BOOLEAN;
DECLARE c1 CURSOR FOR
SELECT starter_rest
FROM ip_ER_ERA_subtotal_1
ORDER BY Starting_Pitcher, Game_Date, Game_Number;
DECLARE CONTINUE HANDLER FOR NOT FOUND
SET end_of_cursor := TRUE;
TRUNCATE TABLE ip_ER_ERA_subtotal_1;
INSERT INTO ip_ER_ERA_subtotal_1 (starter_rest)
SELECT starter_rest
FROM ip_ER_ERA_subtotal_1;
SET end_of_cursor := FALSE;
SET prev_year := 0;
OPEN c1;
fetch_loop: LOOP
FETCH c1 INTO pit_id, gdate, prev_date, seq, strt_rst;
IF end_of_cursor THEN
LEAVE fetch_loop;
END IF;
IF YEAR(gdate) != prev_year THEN
SET strt_rst := 0;
SET prev_year := YEAR(gdate);
END IF;
SET strt_rst := gdate - prev_date;
END IF;
UPDATE TABLE ip_ER_ERA_subtotal_1
SET starter_rest = strt_rst
WHERE Starting_Pitcher = pit_id
AND Game_Date = gdate
AND Game_Number = seq;
END LOOP;
CLOSE c1;
END
$$
这是我得到的错误:
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 'IF;
UPDATE TABLE ip_ER_ERA_subtotal_1
SET starter_rest = str' at line 39
这是表格的屏幕截图,其中包含我正在尝试填充的列已创建并具有“NULL”值。
提前感谢您的帮助。
更新:
ALTER TABLE retrosheet.starting_pitcher_game_log ADD COLUMN starter_rest INT;
UPDATE retrosheet.starting_pitcher_game_log AS b,
retrosheet.game AS g
SELECT @prev as previous,
Game_Date
FROM retrosheet.starting_pitcher_game_log
SET b. starter_rest = Game_date-@prev
WHERE b.`Game_ID` = g.`GAME_ID`
出现错误:
[ERROR in query 2] 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 'SELECT @prev as previous,
Game_Date
FROM retrosheet.starting_pitcher_game_log
S' at line 3
提前谢谢你。
更新:这是在新年伊始为 starter_rest 设置 0 值的编辑表:
DROP PROCEDURE IF EXISTS starting_pitcher_stats_rest_time;
DELIMITER $$
CREATE PROCEDURE starting_pitcher_stats_rest_time()
BEGIN
DECLARE pit_id CHAR(10);
DECLARE gdate DATE;
DECLARE seq INT;
DECLARE prev_date DATE;
DECLARE rest_days INT;
DECLARE prev_year YEAR(4);
DECLARE end_of_cursor BOOLEAN;
DECLARE no_table CONDITION FOR SQLSTATE '42S02';
DECLARE c1 CURSOR FOR
SELECT Starting_Pitcher, Game_Date, Game_Number
FROM starting_pitcher_stats
ORDER BY Starting_Pitcher, Game_Date, Game_Number;
DECLARE CONTINUE HANDLER FOR NOT FOUND
SET end_of_cursor := TRUE;
DECLARE EXIT HANDLER FOR no_table
BEGIN
SIGNAL no_table
SET MESSAGE_TEXT = "Work table not initialized. Please call pitcher_stats_reset() before continuing",
MYSQL_ERRNO = 1146;
END;
SET prev_date := 0;
SET end_of_cursor := FALSE;
OPEN c1;
fetch_loop: LOOP
FETCH c1 INTO pit_id, gdate, seq;
IF end_of_cursor THEN
LEAVE fetch_loop;
END IF;
IF YEAR(gdate) != prev_year THEN
SET rest_days := 0;
SET prev_date := 0;
SET gdate := 0;
SET prev_year := YEAR(gdate);
END IF;
IF prev_date = 0 THEN
SET rest_days := 0;
ELSE
SET rest_days := DATEDIFF(gdate, prev_date);
END IF;
SET prev_date := gdate;
UPDATE starting_pitcher_stats
SET starter_rest = rest_days
WHERE Starting_Pitcher = pit_id
AND Game_Date = gdate
AND Game_Number = seq;
END LOOP;
CLOSE c1;
END
$$
DELIMITER ;
这是一张表格截图,显示了新赛季开始时首发休息的过高价值。理想情况下,它会重置为 0:
任何帮助都会很棒。顺便说一句,达尔文,谢谢你——你的帮助很棒!
【问题讨论】:
-
在我看来,您不太可能想使用存储过程来编辑表结构。
-
好的草莓,你能建议怎么做吗?
-
我的观点是,编辑表格是一项非常罕见的活动,您可能只能手动完成
-
好的,我计划将更多变量/字段一一添加到表中,因为我想知道如何从表的其他列中的字段派生它们。然后,我将在 SPSS 和 R 中同时调用其中的许多来对它们进行分析。所以我的想法是尽我所能在前端减少处理时间/资源利用率,以便在我实际进行分析之前访问这些变量。你能分享一下这样做的手动方法是什么吗?提前谢谢你。
-
我认为你应该再看看规范化 - 如果你仍然认为 RDBMS 是正确的解决方案。
标签: mysql datetime stored-procedures