Postgres——IMMUTABLE | STABLE | VOLATILE (2)

作者:瀚高PG实验室 (Highgo PG Lab)- 狮子歌歌
- 如果把状态改掉,改为immutable呢?

又会是什么结果?

postgres=#  alter function nextval(regclass) immutable;
ALTER FUNCTION
//首先,在事务里,因为以下sql每次单独执行,都会被解析一次,所以每次结果也是。
postgres=# begin;
BEGIN
postgres=# select nextval('seq');
 nextval 
---------
      80
(1 row)

postgres=# select nextval('seq');
 nextval 
---------
      81
(1 row)

postgres=# select nextval('seq');
 nextval 
---------
      82
(1 row)

postgres=# commit;
COMMIT

那么,如果是在同一条sql里呢?
postgres=# select nextval('seq'::regclass) from generate_series(1,3);
 nextval 
---------
      83
      83
      83
(3 rows)
可见,结果都是相同的
执行计划的计划器在解析sql并执行的时候,不管你这里有多少条记录,只会执行一次。


- 如果把状态改掉,改为STABLE呢?

//事务里: 每次结果均不同,因为sql被解析了很多次。
postgres=# select nextval('seq');
 nextval 
---------
      87
(1 row)

postgres=# select nextval('seq');
 nextval 
---------
      88
(1 row)

postgres=# select nextval('seq');
 nextval 
---------
      89
(1 row)

postgres=# commit

//如果是在同一条sql中呢?
//可以发现,依旧是不同的,但是请注意,这里涉及到一个 nextval的位置问题:
postgres=# select nextval('seq'::regclass) from generate_series(1,3);
 nextval 
---------
      90
      91
      92
(3 rows)

// 如果将nextval放在where子句里面呢??
//以下示例参考了德哥的blog
PostgreSQL Function volatile,stable,immutable difference between QUERY select and where. 
http://blog.163.com/digoal@126/blog/static/1638770402013111851116709/

//当前是stable状态
postgres=# select currval('seq');
 currval 
---------
     113
(1 row)

// 可以看出这里返回了三行,也就是说 执行了三次nextval函数的结果都是一样的 

postgres=# select * from t where nextval('seq')=114;
 id 
----
  2
  3
  4
(3 rows)

//切换状态为 volatile; 
postgres=# alter function nextval(regclass) volatile;
ALTER FUNCTION
postgres=# select currval('seq');
 currval 
---------
     114
(1 row)
// 这里返回一行,也就是说执行的三次nextval结果均不同
postgres=# select * from t where nextval('seq')=115;
 id 
----
  2
(1 row)
  • 如果状态是IMMUTABLE,where子句是什么情况呢?
postgres=# alter function nextval(regclass) immutable;
ALTER FUNCTION
postgres=#  select currval('seq');
 currval 
---------
     117
(1 row)
//返回三行,说明三次执行返回值相同

postgres=# select * from t where nextval('seq')=118;
 id 
----
  2
  3
  4
(3 rows)
// 这里恰好验证了这个道理,三次执行返回值相同。
postgres=# select nextval('seq'::regclass) from t ;
 nextval 
---------
     119
     119
     119
(3 rows)

postgres=# 

综上所述:VOLATILE
Stable函数在execute时执行.
Immutable函数在plan时执行.
所以stable和immutable仅仅当使用planed query时才有区别
Planed query属于一次plan, 多次execute. Immutable在planed query中也只会执行一次. 而stable函数在这
种场景中是会执行多次的
Immutable稳定性> stable> volatile


  • 3
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值