当前位置: 首页 > news >正文

Postgresql源码(137)执行器参数传递与使用

参考
《Postgresql源码(127)投影ExecProject的表达式执行分析》

0 总结速查

prepare p_04(int,int) as select b from tbl_01 where a = $1 and b = $2为例。

  • custom计划中,在表达式计算中使用参数的值,因为custom计划会带参数值,所以表达式计算时不需要从参数列表中取值,直接EEO_CASE(EEOP_FUNCEXPR_STRICT)计算即可。
  • generic计划中,在表达式计算中使用参数的值,generic计划不带参数值,所以需要多走一步EEO_CASE(EEOP_PARAM_EXTERN)、EEO_CASE(EEOP_FUNCEXPR_STRICT)。具体调用ExecEvalParamExtern函数拿到参数值。
  • generic计划中,使用参数的节点会放一个Param。

1 执行器如何使用参数?

在下面例子中,execute语句执行时带了两个参数,执行器是在哪里带入参数执行的?下面做一些分析。

prepare p_04(int,int) as select b from tbl_01 where a = $1 and b = $2;
execute p_04(2,200);

带入参数的位置是PortalStart函数。

extern void PortalStart(Portal portal, ParamListInfo params, int eflags, Snapshot snapshot);

PortalStart的第二个参数可以接受参数列表ParamListInfo,从代码上看,PortalStart有三处调用位置:

exec_simple_queryPortalStart(portal, NULL, 0, InvalidSnapshot)exec_bind_messagePortalStart(portal, params, 0, InvalidSnapshot)ExecuteQueryPortalStart(portal, paramLI, eflags, GetActiveSnapshot())SPI_cursor_open_internalPortalStart(portal, paramLI, 0, snapshot)
  1. exec_simple_query:执行简单SQL语句,不需要传参。
  2. exec_bind_message:PEB协议中的B阶段,绑定参数。
  3. ExecuteQuery:SQL语法提供的PBE协议,在execute阶段,绑定参数。
  4. SPI_cursor_open_internal:PL中打开游标时,绑定参数。

下面对3、4两种情况展开分析。

2 execute执行时执行器的传参

栗子:

create table tbl_01(a int, b int);
insert into tbl_01 values (1,100);
insert into tbl_01 values (2,200);
prepare p_04(int,int) as select b from tbl_01 where a = $1 and b = $2;
execute p_04(2,200);

execute p_04(2,200); 执行时,PortalStart会带入ParamListInfo。
在这里插入图片描述

2.1 问题一:ParamListInfo的来源?

ExecuteQueryEvaluateParams// 准备计算参数表达式的值exprstates = ExecPrepareExprList(params, estate)makeParamListretval->parserSetup = paramlist_parser_setup// paramlist_parser_setup//   pstate->p_paramref_hook = paramlist_param_ref//// paramlist_param_ref//   param = makeNode(Param)//   param->paramkind = PARAM_EXTERN//   param->paramid = paramno//   ...//   钩子函数中生成Param,该实例不会走这个钩子,注意Param结构是不带值的,只用于中间过程。// 走表达式计算参数的值// 注意值都在paramLI->params[i]->value中i = 0;foreach(l, exprstates){ExprState  *n = (ExprState *) lfirst(l);ParamExternData *prm = &paramLI->params[i];prm->ptype = param_types[i];prm->pflags = PARAM_FLAG_CONST;prm->value = ExecEvalExprSwitchContext(n,GetPerTupleExprContext(estate),&prm->isnull);i++;}

生成ParamListInfo(包含参数的全部信息,包括值)

paramLI = {paramFetch = 0x0,paramFetchArg = 0x0,paramCompile = 0x0,paramCompileArg = 0x0,parserSetup = 0x8357c1 <paramlist_parser_setup>,parserSetupArg = 0x3238da8,paramValuesStr = 0x0,numParams = 2,params = 0x3238de8}

2.2 问题二:ParamListInfo的使用位置?

custom plan

前五次执行会生成customplan,customplan在GetCachedPlan中生成,customplan计划是带着参数生成的(按参数定制的计划,更准确,但每次参数变了都要重新生成),所以计划中会有参数的具体值,执行时不会使用执行器带入的ParamListInfo。
在这里插入图片描述
构造customplan时,会带入参数生成计划:
在这里插入图片描述

ExecQual调用表达式框架计算where a = $1 and b = $2,ExecQual函数进入表达计算。

ExecScanfor (;;)slot = ExecScanFetch...if (qual == NULL || ExecQual(qual, econtext))...return slot

ExecQual表达式计算流程:

  1. EEO_CASE(EEOP_SCAN_FETCHSOME)
    • 从econtext->ecxt_scantuple读取到scanslot(当前要处理的一行数据)slot_getsomeattrs函数确保这一行数据中,至少有op->d.fetch.last_var个列是可以直接访问的。《Postgresql源码(127)投影ExecProject的表达式执行分析》
  2. EEO_CASE(EEOP_SCAN_VAR)
    • 从行中拿到需要列的值。《Postgresql源码(127)投影ExecProject的表达式执行分析》
  3. EEO_CASE(EEOP_FUNCEXPR_STRICT)
    • 计算where中第一个条件
    • fcinfo : int4eq
    • arg1 : 2
    • arg2 : 2
  4. EEO_CASE(EEOP_QUAL)
  5. EEO_CASE(EEOP_FUNCEXPR_STRICT)
    • 计算where中第二个条件
    • fcinfo : int4eq
    • arg1 : 200
    • arg2 : 200
  6. EEO_CASE(EEOP_QUAL)

generic plan

第六次执行时,choose_custom_plan返回false,BuildCachedPlan时没有传入任何参数构造generic plan(通用执行计划,可以接受任何参数,不用每次都生成计划,但没有customplan精确,毕竟这里没有给参数)
在这里插入图片描述
执行execute p_04(2,200);给的两个参数明显是用于过滤条件的,所以在ExecScan→ExecQual中寻找使用的位置:
在这里插入图片描述

在ExecEvalParamExtern函数中,从econtext->ecxt_param_list_info中拿到参数值,返回给表达式框架:

ExecEvalParamExtern(ExprState *state, ExprEvalStep *op, ExprContext *econtext)
{ParamListInfo paramInfo = econtext->ecxt_param_list_info;int			paramId = op->d.param.paramid;if (likely(paramInfo &&paramId > 0 && paramId <= paramInfo->numParams)){ParamExternData *prm;ParamExternData prmdata;......prm = &paramInfo->params[paramId - 1];......*op->resvalue = prm->value;*op->resnull = prm->isnull;return;}}......
}

最终ExecScan在loop中,拿到的slot经过ExecQual的计算,决定是否保留该元组。

ExecQual调用表达式框架计算where a = $1 and b = $2,通过ExecEvalParamExtern函数拿到$1$2的值,完成计算,放回true OR false。

ExecScanfor (;;)slot = ExecScanFetch...if (qual == NULL || ExecQual(qual, econtext))...return slot

表达式计算流程:

  1. EEO_CASE(EEOP_SCAN_FETCHSOME)
  2. EEO_CASE(EEOP_SCAN_VAR)
  3. EEO_CASE(EEOP_PARAM_EXTERN)
  4. EEO_CASE(EEOP_FUNCEXPR_STRICT)
    • int4eq
    • arg1 : 2
    • arg2 : 2
  5. EEO_CASE(EEOP_QUAL)
  6. EEO_CASE(EEOP_SCAN_VAR)
  7. EEO_CASE(EEOP_PARAM_EXTERN)
  8. EEO_CASE(EEOP_FUNCEXPR_STRICT)
    • int4eq
    • arg1 : 200
    • arg2 : 200

从计划上来看,参数的位置是两个Param。
在这里插入图片描述

3 游标打开时执行器的传参

create table tbl_01(a int, b int);
insert into tbl_01 values (1,100);
insert into tbl_01 values (2,200);do $$
declareres int;c_04 CURSOR (p1 int, p2 int) FOR select b from tbl_01 where a = p1 and b = p2;
beginopen c_04(2,200);fetch c_04 into res;raise notice '%',res;
end; $$;

PL的参数在transform阶段已经转成const了,所以执行类似customplan:
在这里插入图片描述

fetch堆栈:
在这里插入图片描述

相关文章:

Postgresql源码(137)执行器参数传递与使用

参考 《Postgresql源码&#xff08;127&#xff09;投影ExecProject的表达式执行分析》 0 总结速查 prepare p_04(int,int) as select b from tbl_01 where a $1 and b $2为例。 custom计划中&#xff0c;在表达式计算中使用参数的值&#xff0c;因为custom计划会带参数值&…...

韩国恋爱游戏:阿西, 美女室友竟然…?百度网盘下载

​ 故事情节/出场人物 [阿西, 美女室友竟然…&#xff1f;]是一款 FMV 真人视频恋爱游戏&#xff0c;你将以第一人称与5位美女室友一起体验别样合租生活。 在本作中&#xff0c;您将扮演合租公寓的房东男主 吴宥万(直译:牛奶男)&#xff0c;一直独来独往的你&#xff0c;生活…...

一个运维牛人对运维规则的10个总结

一个运维牛人对运维规则的10个总结 在运维领域&#xff0c;经验和流程往往决定了系统的稳定性与可靠性。一个运维人&#xff0c;总结出了以下10条运维规则&#xff0c;涵盖了从基础管理到高级策略的全面内容&#xff0c;旨在帮助运维人员更好地应对各种挑战&#xff0c;确保系…...

Istio基本概念及部署

一、Istio架构及组件 Istio服务网格在逻辑上分为数据平面和控制平面。 控制平面&#xff1a;使用全新的部署模式&#xff1a;Istiod&#xff0c;这个组件负责处理Sidecar注入&#xff0c;证书颁发&#xff0c;配置管理等功能&#xff0c;替代原有组件&#xff0c;降低复杂度&…...

基于 Python 的 Django 框架开发的电影推荐系统

项目简介&#xff1a;本项目是基于 Python 的 Django 框架开发的电影推荐系统&#xff0c;主要功能包括&#xff1a; 电影信息爬取&#xff1a;获取并更新电影数据。数据展示&#xff1a;提供电影数据的列表展示。推荐系统&#xff1a;基于协同过滤算法实现个性化推荐。用户系…...

离线数仓开发SQL编写和调试的最佳实践(如何又快又好完成任务,学会几条就不用当很辛苦的牛马)

目录 在开发阶段对数据进行抽样 理论基础 实践应用 使用Hive进行数据采样 使用Spark进行数据采样 采用CTE模块化设计 逐步验证 逐步验证案例实践: 验证sales_data CTE: 验证ranked_sales CTE: 验证top_sales CTE: 结论 用Doris或Impala等更快查询的代替Hive …...

PostgreSQL 增量备份:保护你的数据资产

全文目录&#xff1a; 开篇语&#x1f4dc; 前言&#x1f4da; 增量备份概述&#x1f511; 增量备份的优势 &#x1f6e0;️ PostgreSQL 增量备份实施步骤&#x1f31f; 环境准备&#x1f680; 第一步&#xff1a;全量备份⏳ 第二步&#xff1a;定期增量备份&#x1f504; 第三…...

字节青训-寻找最大葫芦

问题描述 在一场经典的德州扑克游戏中&#xff0c;有一种牌型叫做“葫芦”。“葫芦”由五张牌组成&#xff0c;其中包括三张相同牌面值的牌 aa 和另外两张相同牌面值的牌 bb。如果两个人同时拥有“葫芦”&#xff0c;我们会优先比较牌 aa 的大小&#xff0c;若牌 aa 相同则再比…...

el-checkbox勾选一个变成了勾选所有

问题&#xff1a; el-checkbox完成后勾选一个选项变成了所有选项都勾选了。非model值不正确&#xff0c;我的model值绑定的是数组&#xff0c;但是还是勾选一个变成了勾选多个。 解决 因为勾选的内容比较简单&#xff0c;且值不需要入库&#xff0c;所以我最开始定义的option为…...

ExpandingCard扩展卡片

文章目录 演示效果分析思路核心代码总结 源码 演示效果 分析思路 使用flex布局&#xff0c;每个卡片的宽度都由flex进行灵活调整交互可以增加和删除active&#xff0c;来实现宽度扩增和恢复还需要使用transition进行动画过渡&#xff0c;使得平滑切换 核心代码 首先创建一个…...

移远通信推出八款天线新品,覆盖5G、4G、Wi-Fi和LoRa领域

近日&#xff0c;全球领先的物联网整体解决方案供应商移远通信宣布&#xff0c;再次推出八款高性能天线新品&#xff0c;进一步丰富其天线产品阵容&#xff0c;更好地满足全球客户对高品质天线的更多需求。具体包括5G超宽带天线YECT005W1A和YECT004W1A、5G天线YECT028W1A、4G天…...

MySQL 9从入门到性能优化-创建触发器

【图书推荐】《MySQL 9从入门到性能优化&#xff08;视频教学版&#xff09;》-CSDN博客 《MySQL 9从入门到性能优化&#xff08;视频教学版&#xff09;&#xff08;数据库技术丛书&#xff09;》(王英英)【摘要 书评 试读】- 京东图书 (jd.com) MySQL9数据库技术_夏天又到了…...

UE5 第三人称学习之动画 control rig

这个东西和建模软件里有的是一个东西&#xff0c;然后IK就是你动脚&#xff0c;他帮你算出小腿大腿该怎么动&#xff0c;FK就是你自己动了大腿&#xff0c;摆小腿&#xff0c;然后再摆脚 就是给每一根骨骼搞一个控制器&#xff0c;给他一个容易选中和操作更明显的图形作为控制…...

C++之--初见模板初阶

一、泛型编程 为了实现一个通用的函数&#xff0c;在此之前&#xff0c;我们学过函数重载&#xff0c;使用函数重载虽然可以实现&#xff0c;但是有一下几个不好的地方&#xff1a; 1. 重载的函数仅仅是类型不同&#xff0c;代码复用率比较低&#xff0c;只要有新类型出现时&a…...

Nature|用于无线监测颅内信号的植入式柔性超声波传感器(柔性传感/健康监测/植入式电子/水凝胶)

华中科技大学臧剑锋(Jianfeng Zang)、华中科技大学同济医学院附属协和医院姜晓兵(Xiaobing Jiang)和新加坡南洋理工大学陈晓东(Xiaodong Chen)团队,在《Nature》上发布了一篇题为“Injectable ultrasonic sensor for wireless monitoring of intracranial signals”的论…...

【和AI的《趣味》聊天】01 AI:你找茬是吧(

我&#xff1a; 以下哪个选项是中文&#xff1f; A.Chinese B.英文 AI&#xff1a; 我&#xff1a; 这不对吧&#xff0c;我说的是那个选项的语言是中文 AI&#xff1a; 非常抱歉&#xff0c;我之前的回答有误。您问的是哪个选项的语言是中文&#xff0c;那么答案应该是…...

“发放父作业单”是“过数”用例里面的内容吗

刘京城 2020-4-14 23:01 。。。。(注&#xff1a;这是一个人的昵称&#xff0c;不是省略号) 首先&#xff0c;执行者是同一个&#xff0c;那么思考焦点要关注“过数”用例是不是“发放父作业单”用例的一个步骤&#xff0c;和行为操作的频率无关&#xff0c;而是和责任有关&am…...

Linux补基础之:网络配置

目录 一、检查主机与虚拟机是否能正常通信 二、网络的连接模式 桥接模式 流程 特点 NAT模式 流程 特点 仅主机 流程 特点 三、修改静态IP 四、可能遇到的问题 防火墙 DNS 五、主机名更改 六、登录服务器 实际的大数据管理中&#xff0c;会有由很多服务器构成的…...

【flink】之kafka到kafka

一、概述 本文档旨在介绍如何使用Apache Flink从Kafka接收数据流&#xff0c;并将处理后的数据写入到另一个Kafka Topic中。Apache Flink是一个开源的流处理框架&#xff0c;能够处理无界和有界数据流&#xff0c;并且支持高吞吐量和低延迟的数据处理。通过Flink与Kafka的集成…...

微信小程序时间弹窗——年月日时分

需求 1、默认当前时间2、选择时间弹窗限制最大值、最小值3、每次弹起更新最大值为当前时间&#xff0c;默认值为上次选中时间4、 minDate: new Date(2023, 10, 1).getTime(),也可以传入时间字符串new Date(2023-10-1 12:22).getTime() html <view class"flex bb ptb…...

攻防世界 misc题GFSJ1129-【您看我还有机会吗?】

1.工具:010editor、VMware(Ubuntu、binwalk)、在线 Brainfuck解密、CTF-Tools、ImageStrike、7zFM 2.解题: 方法一(最初的解法): 下载附件后,我们打开,发现有一张图片,点击后发现要密码,我发现没有任何密码的提示,怀疑是伪加密(由于篇幅较长,我后续会在写一篇…...

GME-Qwen2-VL-2B-Instruct效果扩展:多风格艺术画作的理解与情感分析展示

GME-Qwen2-VL-2B-Instruct效果扩展&#xff1a;多风格艺术画作的理解与情感分析展示 最近在玩一个挺有意思的视觉语言模型&#xff0c;叫GME-Qwen2-VL-2B-Instruct。它个头不大&#xff0c;但能力挺让人意外。我突发奇想&#xff0c;把它当成了一个“数字艺术评论员”&#xf…...

Fish-Speech-1.5 API调用教程:Python脚本批量生成语音

Fish-Speech-1.5 API调用教程&#xff1a;Python脚本批量生成语音 1. 为什么选择Fish-Speech-1.5进行批量语音生成 在日常工作中&#xff0c;我们经常遇到需要将大量文本转换为语音的场景。无论是为视频内容生成旁白&#xff0c;还是为电子书制作有声版本&#xff0c;传统的人…...

Xinference+tao-8k实战:快速构建文档相似度分析工具

Xinferencetao-8k实战&#xff1a;快速构建文档相似度分析工具 1. 从想法到工具&#xff1a;为什么你需要一个文档相似度分析器 想象一下这个场景&#xff1a;你手头有几百份技术文档、产品说明或者客户反馈&#xff0c;你想快速找出哪些文档在讨论同一个主题&#xff0c;或者…...

[特殊字符] Local Moondream2图文对话教程:详细步骤实现自定义问题提问

Local Moondream2图文对话教程&#xff1a;详细步骤实现自定义问题提问 1. 引言&#xff1a;让电脑拥有"眼睛"的智能工具 你是否曾经希望电脑能像人一样看懂图片&#xff0c;并且回答关于图片内容的问题&#xff1f;Local Moondream2就是这样一款神奇的工具&#x…...

别再手动打字了!用uniapp+百度语音识别,5分钟搞定语音转文字功能(附完整代码)

用UniApp百度语音识别实现高效语音转文字功能 在移动应用开发中&#xff0c;语音输入正逐渐成为提升用户体验的关键功能。想象一下&#xff0c;用户无需费力敲击虚拟键盘&#xff0c;只需轻按按钮说话&#xff0c;文字就能自动出现在输入框中——这种交互方式不仅自然流畅&…...

【TC3xx芯片】Endinit机制实战:从解锁到上锁的完整代码解析

1. TC3xx芯片Endinit机制的核心作用 在嵌入式系统开发中&#xff0c;寄存器保护是确保系统稳定性的关键机制。TC3xx系列芯片采用的Endinit&#xff08;End of initialization&#xff09;保护方案&#xff0c;就像给重要寄存器装了一把智能密码锁。想象一下&#xff0c;你家的保…...

Debian GNU/Linux12高效运维指南(网络配置、远程管理、软件更新与安全防护)

1. Debian GNU/Linux12网络配置实战 刚接触Debian GNU/Linux12的朋友们&#xff0c;网络配置可能是你们遇到的第一个挑战。别担心&#xff0c;我会用最直白的方式带你们搞定这个环节。网络配置就像给新房子拉网线&#xff0c;得先把基础线路接好&#xff0c;后续的上网、远程控…...

WeChatExporter:免费开源工具,轻松备份你的微信聊天记录到电脑

WeChatExporter&#xff1a;免费开源工具&#xff0c;轻松备份你的微信聊天记录到电脑 【免费下载链接】WeChatExporter 一个可以快速导出、查看你的微信聊天记录的工具 项目地址: https://gitcode.com/gh_mirrors/wec/WeChatExporter 你是否曾经担心过手机丢失、系统崩…...

Piping Server开发者指南:如何基于流传输构建自己的应用

Piping Server开发者指南&#xff1a;如何基于流传输构建自己的应用 【免费下载链接】piping-server Infinitely transfer between every device over pure HTTP with pipes or browsers 项目地址: https://gitcode.com/gh_mirrors/pi/piping-server Piping Server是一个…...