您的位置:首页 > 数据库 > MySQL

mysql 游标+存储过程

2015-10-09 17:10 531 查看
1.首先需要注意的是mysql中游标必须要建立在存储过程中

2.直接上sql

-- 查询当天数据
SELECT in_flow+out_flow
FROM water_meter_data
WHERE 1=1 and date(sys_read_time) = curdate()-1
ORDER BY (in_flow+out_flow) DESC
LIMIT 0,1

-- 查询前一天数据
SELECT in_flow+out_flow
FROM water_meter_data
WHERE 1=1 and date(sys_read_time) = curdate()
ORDER BY (in_flow+out_flow) DESC
LIMIT 0,1

-- 查询当天数据
SELECT MAX(in_flow+out_flow)
FROM water_meter_data
WHERE 1=1 and date(sys_read_time) = curdate()

-- 游标 + 存储过程 

-- 例子
drop procedure if exists useCursor;
delimiter 
CREATE PROCEDURE useCursor()
  BEGIN
    DECLARE oneAddr varchar(150) default '';
    DECLARE allAddr varchar(150) default '';
    DECLARE done INT DEFAULT 0;
    DECLARE curl CURSOR FOR SELECT addr FROM energy.person;
    DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = 1;
    OPEN curl;
    REPEAT
      FETCH curl INTO oneAddr;
      IF NOT done THEN
        set oneAddr = CONCAT(oneAddr, ';');
        set allAddr = CONCAT(allAddr, oneAddr);
      END IF;
    UNTIL done END REPEAT;
    CLOSE curl;
    select allAddr;
  END;
call useCursor();

-- 我的

-- 定义游标
drop procedure if exists water_total;-- 检查存储过程是否存在
delimiter; -- 分隔符
CREATE PROCEDURE energy.water_total()-- 创建存储过程
BEGIN
		-- 局部变量的定义 declare
		DECLARE meter_id INT DEFAULT 0;-- 设备id
    DECLARE flow_now INT DEFAULT 0;-- 当天的流量
    DECLARE flow_before INT DEFAULT 0;-- 前一天的流量
		DECLARE build_id INT DEFAULT 0;-- 建筑id
		DECLARE room_id INT DEFAULT 0;-- 房间id
		DECLARE done INT DEFAULT 0; --  控制游标结束

    DECLARE cur_meter CURSOR FOR 
						SELECT energy.meter_info.hid ,energy.meter_info.buildid,energy.meter_info.consumer_id 
						FROM energy.meter_info where energy.meter_info.meter_type='5';-- 声明游标

    DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = 1;-- 控制游标的结束

		-- DECLARE CONTINUE HANDLER FOR SQLSTATE '02000' SET done = 1;-- 这把 游标 异常后 捕捉 并设置 循环使用 变量 id 为 null 跳出循环
    OPEN cur_meter;-- 开启游标

    REPEAT -- repeat循环

      FETCH cur_meter INTO meter_id,build_id,room_id;-- 把第一行记录写入变量里,游标也随着指向第一行
	-- SELECT meter_id;
			IF NOT done THEN -- 判断循环是否结束
				
				 -- 取当天的流量和最大值
         SELECT  max(energy.water_meter_data.in_flow+energy.water_meter_data.out_flow) INTO flow_now
				 FROM  energy.water_meter_data
				 WHERE 1=1 and date(energy.water_meter_data.sys_read_time) = curdate() and energy.water_meter_data.meter_id = meter_id;

				 -- 取昨天的流量和最大值
         SELECT  max(energy.water_meter_data.in_flow+energy.water_meter_data.out_flow) INTO flow_before
				 FROM  energy.water_meter_data
				 WHERE 1=1 and date(energy.water_meter_data.sys_read_time) = curdate()-1 and energy.water_meter_data.meter_id = meter_id;
					-- 判断是否为空
					IF (flow_now IS NOT NULL) AND (flow_before IS NOT NULL) THEN
						  -- 插入到水表统计表中
						 INSERT INTO energy.water_data_total(energy.water_data_total.meter_id,energy.water_data_total.build_id,
													energy.water_data_total.room_id,energy.water_data_total.water_flow,
													energy.water_data_total.create_date,energy.water_data_total.create_user)
						 VALUES(meter_id,build_id,room_id,flow_now-flow_before,date(NOW()),'admin');
					END IF;
      END IF;
    UNTIL done END REPEAT; -- repeat循环结束
    CLOSE cur_meter;-- 注意,用完后必须关闭
  END;

-- 调用存储过程
CALL energy.water_total();
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: