好贷网好贷款

PostgreSQL 游标处理

发布时间:2016-12-5 12:33:19 编辑:www.fx114.net 分享查询网我要评论
本篇文章主要介绍了"PostgreSQL 游标处理",主要涉及到PostgreSQL 游标处理方面的内容,对于PostgreSQL 游标处理感兴趣的同学可以参考一下。

PostgreSQL 游标处理 简单循环处理I  此写法是先取一条数据,然后判断循环条件  -- 清空日志表. Test=# truncate table log_table; TRUNCATE TABLE Test=# select * from test_main;  id | value ----+-------   1 | ONE   2 | TWO   4 | FOUR (3 行记录) CREATE OR REPLACE FUNCTION TestCursor() RETURNS void AS $$ DECLARE   -- 定义游标.   c_test_main CURSOR FOR     SELECT id, value FROM test_main;   -- 定义存储数据的变量.   v_id    INT;   v_value VARCHAR(10); BEGIN   -- 打开游标.   OPEN c_test_main;   -- 填充数据.   FETCH c_test_main INTO v_id, v_value;   -- 假如检索到了数据,才处理.   while found loop       INSERT INTO log_table VALUES (v_value); -- 填充下一条数据.     FETCH c_test_main INTO v_id, v_value;   end loop;       -- 关闭游标   CLOSE c_test_main; END; $$ LANGUAGE plpgsql; Test=# select TestCursor();  testcursor ------------ (1 行记录) Test=# select * from log_table;  log_text ----------  ONE  TWO  FOUR (3 行记录) 如果 SQL 语句中, 列的数量很多, 那么定义很多的变量,对应没一列。 开发、维护成本都会比较高。 这种情况下, 可以采用  表名%rowtype  的方式, 只定义一个变量来进行处理. -- 清空日志表. Test=# truncate table log_table; TRUNCATE TABLE CREATE OR REPLACE FUNCTION TestCursor() RETURNS void AS $$ DECLARE   -- 定义游标.   c_test_main CURSOR FOR     SELECT id, value FROM test_main ORDER BY id DESC;   -- 定义存储数据的变量.   v_main_data  test_main%ROWTYPE; BEGIN   -- 打开游标.   OPEN c_test_main;   -- 填充数据.   FETCH c_test_main INTO v_main_data;   -- 假如检索到了数据,才处理.   while found loop       INSERT INTO log_table VALUES (v_main_data.value); -- 填充下一条数据.     FETCH c_test_main INTO v_main_data;   end loop;       -- 关闭游标   CLOSE c_test_main; END; $$ LANGUAGE plpgsql; Test=# select TestCursor();  testcursor ------------ (1 行记录) Test=# select * from log_table;  log_text ----------  FOUR  TWO  ONE (3 行记录) 简单循环处理II  此写法是先开始循环,然后取数据,然后判断条件  -- 清空日志表. Test=# truncate table log_table; TRUNCATE TABLE Test=# select * from test_main;  id | value ----+-------   1 | ONE   2 | TWO   4 | FOUR (3 行记录) CREATE OR REPLACE FUNCTION TestCursor2() RETURNS void AS $$ DECLARE   -- 定义游标.   c_test_main CURSOR FOR     SELECT id, value FROM test_main;   -- 定义存储数据的变量.   v_id    INT;   v_value VARCHAR(10); BEGIN   -- 打开游标.   OPEN c_test_main;      LOOP       -- 填充数据.     FETCH c_test_main INTO v_id, v_value;     -- 假如没有检索到数据,结束循环处理     Exit when NOT found; -- 游标每一行的实际操作.     INSERT INTO log_table VALUES (v_value);   END LOOP;       -- 关闭游标   CLOSE c_test_main; END; $$ LANGUAGE plpgsql; Test=# select TestCursor2();  testcursor2 ------------- (1 行记录) Test=# select * from log_table;  log_text ----------  ONE  TWO  FOUR (3 行记录) 支持来回滚动的游标  -- 清空日志表. Test=# truncate table log_table; TRUNCATE TABLE -- 为达到测试效果, 多加几行测试数据. INSERT INTO test_main(id, value) VALUES (11, 'ONEONE'); INSERT INTO test_main(id, value) VALUES (12, 'ONETWO'); INSERT INTO test_main(id, value) VALUES (13, 'ONETHREE'); Test=# SELECT id, value FROM test_main ORDER BY id;  id |  value ----+----------   1 | ONE1   2 | TWO1   4 | FOUR1  11 | ONEONE  12 | ONETWO  13 | ONETHREE (6 行记录) CREATE OR REPLACE FUNCTION TestCursorScroll() RETURNS void AS $$ DECLARE   -- 定义游标.   c_test_main SCROLL CURSOR FOR     SELECT id, value FROM test_main ORDER BY id;   -- 定义存储数据的变量.   v_main_data  test_main%ROWTYPE; BEGIN   -- 打开游标.   OPEN c_test_main;   -- 填充数据.   FETCH FIRST FROM c_test_main INTO v_main_data;   INSERT INTO log_table VALUES ('游标第一行:' || v_main_data.value);      -- 填充数据.   FETCH LAST FROM c_test_main INTO v_main_data;   INSERT INTO log_table VALUES ('游标最末行:' || v_main_data.value);      -- 填充数据.   FETCH ABSOLUTE 3 FROM c_test_main INTO v_main_data;   INSERT INTO log_table VALUES ('游标绝对第3行:' || v_main_data.value);   -- 填充数据.   FETCH RELATIVE 2 FROM c_test_main INTO v_main_data;   INSERT INTO log_table VALUES ('游标相对第2行:' || v_main_data.value);      -- 填充数据.   FETCH PRIOR  FROM c_test_main INTO v_main_data;   INSERT INTO log_table VALUES ('游标上一行:' || v_main_data.value);   -- 填充数据.   FETCH NEXT  FROM c_test_main INTO v_main_data;   INSERT INTO log_table VALUES ('游标下一行:' || v_main_data.value);        -- 关闭游标   CLOSE c_test_main; END; $$ LANGUAGE plpgsql; Test=# select TestCursorScroll() ;  testcursorscroll ------------------ (1 行记录) Test=# select * from log_table;        log_text ----------------------  游标第一行:ONE1  游标最末行:ONETHREE  游标绝对第3行:FOUR1  游标相对第2行:ONETWO  游标上一行:ONEONE  游标下一行:ONETWO (6 行记录) 带参数的游标  这里同时需要使用前面外键约束的 test_sub 表  -- 清空日志表. Test=# truncate table log_table; TRUNCATE TABLE CREATE OR REPLACE FUNCTION TestCursorMainSub() RETURNS void AS $$ DECLARE   -- 定义游标(主表).   c_test_main CURSOR FOR     SELECT id, value FROM test_main;   -- 保存主表游标数据的变量   v_main_data  test_main%ROWTYPE;      -- 定义游标(子表).   c_test_sub CURSOR(p_main_id INT) IS     SELECT id, main_id, value     FROM test_sub     WHERE main_id = p_main_id;   -- 保存子表游标数据的变量   v_sub_data  test_sub%ROWTYPE; BEGIN   -- 打开游标(主表).   OPEN c_test_main;   -- 开始循环处理(主表).   LOOP       -- 填充数据(主表).     FETCH c_test_main INTO v_main_data;     -- 假如没有检索到(主表)数据,结束循环处理     Exit when NOT found;     -- 主表每一行的实际操作.     INSERT INTO log_table VALUES ( 'Main:' || v_main_data.value );     -- 打开游标(子表).     OPEN c_test_sub(v_main_data.id);     -- 开始循环处理(子表).     LOOP       -- 填充数据(子表).       FETCH c_test_sub INTO v_sub_data;       -- 假如没有检索到(主表)数据,结束循环处理       Exit when NOT found;       -- 子表每一行的实际操作.       INSERT INTO log_table VALUES ( '-->Sub:' || v_sub_data.value );     END LOOP;     -- 关闭游标(子表).     CLOSE c_test_sub;   END LOOP;       -- 关闭游标(主表).   CLOSE c_test_main; END; $$ LANGUAGE plpgsql; Test=# select TestCursorMainSub();  testcursormainsub ------------------- (1 行记录) Test=# select * from log_table;     log_text -----------------  Main:ONE  -->Sub:ONEONE  Main:TWO  -->Sub:TWOTWO  Main:FOUR  -->Sub:FOURFOUR (6 行记录) 用于更新的游标  CREATE OR REPLACE FUNCTION TestUpdateCursor() RETURNS void AS $$ DECLARE   -- 定义游标.   c_test_main CURSOR FOR     SELECT id, value FROM test_main FOR UPDATE ;   -- 定义存储数据的变量.   v_main_data  test_main%ROWTYPE; BEGIN   -- 打开游标.   OPEN c_test_main;   LOOP       -- 填充数据.     FETCH c_test_main INTO v_main_data;     -- 假如没有检索到数据,结束循环处理     Exit when NOT found; -- 游标每一行的实际操作.      -- 更新数据.     UPDATE        test_main     SET       value = value || '1'     WHERE        CURRENT OF c_test_main;   END LOOP;       -- 关闭游标   CLOSE c_test_main; END; $$ LANGUAGE plpgsql; Test=# select TestUpdateCursor();  testupdatecursor ------------------ (1 行记录) Test=# select * from test_main;  id | value ----+-------   1 | ONE1   2 | TWO1   4 | FOUR1 (3 行记录) FOR的使用  -- 清空日志表. Test=# truncate table log_table; TRUNCATE TABLE CREATE OR REPLACE FUNCTION TestCursorFor() RETURNS void AS $$ DECLARE   -- 定义存储数据的变量.   v_main_data RECORD; BEGIN   FOR v_main_data IN SELECT id, value FROM test_main LOOP -- 每一行的实际操作.     INSERT INTO log_table VALUES (v_main_data.value);   END LOOP;  END; $$ LANGUAGE plpgsql; Test=# SELECT TestCursorFor();  testcursorfor --------------- (1 行记录) Test=# select * from log_table;  log_text ----------  ONE1  TWO1  FOUR1 (3 行记录)

上一篇:IOS NSUserDefaults 小技巧
下一篇:【热门主题:喵星人高清桌面壁纸】

相关文章

相关评论