如何用 esProc 补充数据库 SQL 的缺失能力

某些数据库 SQL 缺失必要的能力,通常要编写大段的代码,才能间接实现类似的功能,有些情况甚至要改用存储过程,连结构都变了。常见的比如:生成时间序列、保持分组子集、动态行列转换、自然序号、相对位置、按序列和集合生成多条记录、累积计算、条件分组、跨库计算、集合计算、序列计算、自关联结构、递归计算、对齐式关联等。用下面几个例子快速感受一下。

生成时间序列:某库表的 Time 字段是时间,时间的间隔有时大于 1 分钟。

TimeValue
10:10:053
10:11:064
10:13:135
10:13:199
10:13:328
10:14:352

现在要将数据每分钟分成一个窗口,补上缺失的窗口,对每个窗口统计 4 个值:前一个窗口的最后一条 start_value;本窗口的最后一条;本窗口的最小值;本窗口的最大值。第一分钟的 start_value 用本窗口的第一条记录;如果缺少某窗口的数据,则用前一个窗口的最后一条代替。

startendstart_valueend_valueminmax
10:10:0010:11:003333
10:11:0010:12:003444
10:12:0010:13:004444
10:13:0010:14:004859
10:14:0010:15:008222

很多数据库的 SQL 没有方便的方法生成月份序列,很多数据库要用多层嵌套查询 + 多个窗口函数才能间接实现。

保持分组子集:某表存储多个账号在多个日期发生的事件。

RowAccount NumberDate
110012011-01-10
210012011-02-01
310012011-02-20
410012011-02-22
520012011-04-11
620012012-01-01
720012012-01-30
820012012-02-09

现在要找出每个账号下符合条件的一对事件,分别是:日期最早的事件 a、距 a 事件 30 天以上的事件中日期最早的事件 b。

RowAccount NumberDate
110012011-01-10
310012011-02-20
520012011-04-11
620012012-01-01

SQL 分组后必须立刻汇总,很难按条件 b 筛选记录,只能用 join 语句配合多个 CTE 子句间接实现。

动态行列转换:某库表记录了不同产品每个月的销售额,其中产品的值未知。

productmonthamount
AA1100
AA1150
AA2200
AA2120
BB2180
BB2220
CC380

现在要对产品、月份分组,对销售额求和,再将产品由行转列。

monthAABBCC
1250
2320400
380

某些数据库的 SQL 缺失动态行列转换能力,行转列时必须写出列名,很多数据库只能改用存储过程。

esProc SPL 内置丰富的计算类库,可以补充这些数据库 SQL 缺失的能力,比如上面 3 个例子:

"https://c.raqsoft.com.cn/article/1742353802112"


“@从 SQL 到 SPL:计算组内符合条件的一对最小值 - 乾学院”

“从 SQL 到 SPL:Create columns from distinct values of a column - 乾学院”

下面,我们就来尝试一下如何将 esProc 集成到应用中。

先下载 esProc,推荐标准版:集算器 产品下载 | 报表加速器下载-半结构化计算软件下载

下载并安装相应的版本。

安完后,试一下 esProc IDE 是否可以正常访问数据库。先把数据库的 JDBC Driver 放到目录 "[安装目录]\common\jdbc",这是 esProc 的类路径之一。比如 mySQL 的 JDBC:

Picture1png


打开 esProc IDE,找到菜单 "Tool->Connect to Data Source",新建 JDBC 数据源,填入具体数据库的连接信息。下面是一个 mySQL 的数据源:

Picture2png


返回到数据源界面,试着连接数据源,跨库运算时可以同时连接多个数据源。如果数据源名变成粉色,说明配置成功。

Picture3png


在 IDE 中新建脚本,写 SPL 语句,连接 mysql 数据库,加载第 1 个例子的数据:

=connect("mysql").query@x("select * from main")

按 ctrl-F9 执行,可以在 IDE 右边看到执行结果,以数据表的形式呈现,这对调试 SPL 代码很方便。

Picture4png

加载数据正常后,就可以写正式的 SPL 代码了,第 1 个例子:

 A
1=connect("mysql").query@x("select * from main where time>? and time<=?",arg1,arg2)
2=A1.run(Time=time@m(Time))
3=list=periods@s(A2.min(Time),A2.max(Time),60)
4=A2.align@a(list,Time)
5=A4.new(list(#):start, elapse@s(start,60):end, sv=ifn(end_value[-1],~.Value):start_value, ifn(~.m(-1).Value, sv):end_value, ifn(~.min(Value),sv):min, ifn(~.max(Value),sv):max)

先用参数过滤;再将时间改为整分钟数;生成连续分钟的时间序列;将数据按时间序列对齐,每组数据对应一分钟的窗口;按要求用每组数据生成一条新记录。

把上面脚本保存在某个目录中,比如 D:\data\procMain.splx,运行后可以看到结果:

Picture5png

第 2 个例子:

 A
1=connect("mysql").query@x("select * from ventas")
2=A1.group(#2)
3=A2.conj(~1 | ~.select@1((#3 - A2.~1.#3)>30))

加载数据;按 2 个字段分组,但不汇总;取每组第 1 条,再筛选出距第 1 条 30 天以上的记录,也取第 1 条;合并这 2 条记录,最后合并各组的处理结果。

保存成 D:\data\proc2.splx,执行后看结果:

Picture6png


第 3 个例子:

=connect("mysql").query@x("select * from ventas").pivot@s(month;product,sum(amount))

加载数据后动态转置,执行结果:

Picture7png


在 IDE 中调试无误后,就可以把 esProc 集成到 Java 环境中了。
从目录 "[安装目录]\esProc\lib" 下找到 esProc JDBC 相关的 jar 包:esproc-bin-xxxx.jar、icu4j_60.3.jar。

Picture8png


将这两个 jar 包部署到 Java 开发环境的类路径下。
再从目录 "[安装目录]\esProc\config" 下找到 esProc 配置文件 raqsoftConfig.xml,同样部署到 Java 开发环境的类路径下。

Picture9png


配置文件中要改的配置项是 mainPath,这表示脚本等文件的默认路径。注意数据源的信息也在配置文件中。
接下来,就可以编写 Java 代码,通过 esProc JDBC 调用 SPL 脚本了,例子 1:

Class.forName("com.esproc.jdbc.InternalDriver");
Connection con= DriverManager.getConnection("jdbc:esproc:local://");
PreparedStatement st = con.prepareCall("call procMain(?,?)");
st.setTime(1,Time.valueOf("10:00:00"));
st.setTime(2,Time.valueOf("11:00:00"));
ResultSet rs = st.executeQuery();

可以看到,调用 SPL 脚本的过程和调用存储过程是一样的。计算后结果如下:

Picture10png


脚本文件不是必须的,可以把 SPL 脚本转为 SPL 代码,像 SQL 那样嵌入 Java。先在 IDE 中打开例子 2 的脚本文件,选中有代码的单元格 A1-A3,再点击菜单 "Edit->Copy->Code copy",这样就把多行多列的网格代码转成了单行的 SPL 代码,暂存在粘贴板里。

Picture11png


将转换后的 SPL 代码复制到 Java 代码中

Connection con= DriverManager.getConnection("jdbc:esproc:local://");
PreparedStatement st = con.prepareStatement("==connect(\"mysql\").query@x(\"select * from ventas\")\n=A1.group(#2) \n=A2.conj(~1 | ~.select@1((#3 - A2.~1.#3)>30))");
ResultSet rs = st.executeQuery();
可以看到,Java调用SPL代码的过程和调用SQL代码一样。运行后可以看到结果:

可以看到,Java调用SPL代码的过程和调用SQL代码一样。运行后可以看到结果:

Picture12png


有些 SPL 代码比较简单,没必要用 esProc IDE 编写调试,那就可以直接写在 Java 里。比如例子 3,直接在 Java 中嵌入 SPL 代码:

Connection con= DriverManager.getConnection("jdbc:esproc:local://");
PreparedStatement st = con.prepareStatement("=connect(\"mysql\").query@x(\"select * from ventas\").pivot@s(month;product,sum(amount))");
ResultSet rs = st.executeQuery();

执行结果像下面这样:

Picture13png


乾学院上还有很多补充 SQL 缺失能力的例子,开发遇到问题时可以去找找解决办法。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/76075.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

迷你世界脚本脚本常见问题

脚本常见问题 彼得兔 更新时间: 2024-05-22 17:54:44 在查阅开发者学院中的脚本API时&#xff0c;若有任何问题或建议&#xff0c;欢迎通过问卷进行反馈&#xff01;【点我填写问卷】 1.Block中的data在什么地方使用 data使用有具体需求,此处不建议开发者使用。开发者尽可能使…

四、Appium Inspector

一、介绍 Appium Inspector 是一个用于移动应用自动化测试的图形化工具&#xff0c;主要用于检查和交互应用的 UI 元素&#xff0c;帮助生成和调试自动化测试脚本。类似于浏览器的F12(开发者工具),Appium Inspector 的主要作用包括&#xff1a;‌ 1.‌检查 UI 元素‌ …

android11通过白名单卸载安装应用

目录 1.源码路径: 2.准备文件package.conf: 3.安装方法installPackagesLI 4.卸载方法deletePackageX 1.源码路径: frameworks/base/services/core/java/com/android/server/pm/PackageManagerService.java public static final String WHITELIST_PATH="/data/misc/pa…

qt mapFrom返回的QPoint和event->pos()区别和globalPos区别

mousePressEvent 和 eventFilter 里 event.pos 不一样&#xff0c;一定要注意 eventFilter里event.pos 直接返回相对于label左上角的坐标&#xff0c;就不要再mapFrom mousePressEvent 里event.pos 返回是相对于窗口左上角的坐标&#xff0c;需要用mapFrom返回label左上角的…

Hadoop四 Hive语法

一 数据库操作 Hive数据库操作&#xff0c;与MySql有很多都是一致的 创建数据库 create database if not exists myhive; use myhive;查看数据库详细信息 desc database myhive;数据库本质上就是在HDFS之上的文件夹&#xff0c;是一个以.db结尾的目录&#xff0c;默认存…

前端VUE框架理论与应用(10)

1、记住全局注册的行为必须在根 Vue 实例 (通过 new Vue) 创建之前发生。 2、要注意,以 / 开头的嵌套路径会被当作根路径。 这让你充分的使用嵌套组件而无须设置嵌套的路径。 3、注意:在 Vue 实例内部,你可以通过 $router 访问路由实例。因此你可以调用 this.$router.push…

leetcode-单调栈26

关于单调栈的顺序总结&#xff1a; 寻找右边第一个比我大的&#xff1a;从左到右遍历&#xff0c;栈单调递减 寻找左边第一个比我小的&#xff1a;从左到右遍历&#xff0c;栈单调递增 寻找右边第一个比我小的&#xff1a;从右到左遍历&#xff0c;栈单调递增 寻找左边第一个比…

Linux:安装 CentOS 7(完整教程)

文章目录 一、简介二、安装 CentOS 72.1 虚拟机配置2.2 安装CentOS 7 三、连接远程服务器&#xff08;扩展&#xff09;3.1 获取虚拟机 IP 地址3.2 连接远程服务器 四、结语 一、简介 CentOS&#xff08;Community ENTerprise Operating System&#xff09;是一个基于 Linux 的…

Nautilus 正式发布:为 Sui 带来可验证的链下隐私计算

作为 Sui 安全工具包中的强大新成员&#xff0c;Nautilus 现已上线 Sui 测试网。它专为 Web3 开发者打造&#xff0c;支持保密且可验证的链下计算。Nautilus 应用运行于开发者自主管理的可信执行环境&#xff08;Trusted Execution Environment&#xff0c;TEE&#xff09;中&a…

Git完全指南:从入门到精通版本控制 ------- Git 工作流程 (3)

Git工作流程完全指南&#xff1a;从入门到高效协作 引言 Git作为分布式版本控制系统的行业标准&#xff0c;其高效的分支管理能力是团队协作的基石。本文将深入解析标准Git工作流程&#xff0c;助你掌握从代码提交到团队协作的全链路实践。 一、Git核心概念速览 三大工作区域 …

Distortion, Animation Raymarching

这节课的主要目的是对uv进行操作&#xff0c;实现一些动画的效果&#xff0c;实际就是采样的动画 struct texDistort {float2 texScale(float2 uv, float2 scale){float2 texScale (uv - 0.5) * scale 0.5;return texScale;}float2 texRotate(float2 uv, float angle){float…

《vue3学习手记3》

标签的ref属性 vue3和vue2中的ref属性&#xff1a; 用在普通DOM标签上&#xff0c;获取的是DOM节点 ref用在组件标签上&#xff0c;获取的是组件实例对象 区别在于&#xff1a; 1.vue3中person子组件中的数据父组件App不能直接使用&#xff0c;需要引入并使用defineExpose才可…

List基础与难度题

1. 向 ArrayList 中添加元素并打印 功能描述&#xff1a; 程序创建一个空的 ArrayList 集合&#xff0c;用于存储字符串类型的元素。向该 ArrayList 中依次添加指定的字符串元素。使用增强型 for 循环遍历 ArrayList 中的所有元素&#xff0c;并将每个元素打印输出到控制台。 …

楼宇自控系统如何为现代建筑打造安全、舒适、节能方案

在科技飞速发展的当下&#xff0c;现代建筑对功能和品质的要求日益提升。楼宇自控系统作为建筑智能化的核心技术&#xff0c;宛如一位智慧的“管家”&#xff0c;凭借先进的技术手段&#xff0c;为现代建筑精心打造安全、舒适、节能的全方位解决方案&#xff0c;让建筑真正成为…

绿算轻舟系列FPGA加速卡:驱动数字化转型的核心动力【2】

工业与医疗&#xff1a;精准化的幕后推手 在工业4.0与智慧医疗领域&#xff0c;绿算轻舟FPGA加速卡通过实时信号处理与高精度控制&#xff0c;推动关键场景的技术升级。 工业自动化&#xff1a;在机器视觉质检中&#xff0c;实现亚像素级缺陷检测&#xff0c;产线检测速度大幅…

uniapp-商城-22-顶部模块

这里其实很复杂.我们在前面已经说了这个组件 shop-headbar ,这里来继续说。 该组件实现一个高度的显示以及图片展示,包含logo 名称 后台管理以及避让 导航栏 和 手机的状态栏。 1 整体 代码如下: <template><view class="headr" :style="{ hei…

利用Global.asax在ASP.NET Web应用中实现功能

Global.asax文件&#xff08;也称为ASP.NET应用程序文件&#xff09;是ASP.NET Web应用程序中的一个重要文件&#xff0c;它允许您处理应用程序级别和会话级别的事件。下面介绍如何利用Global.asax来实现各种功能。 Global.asax基本结构 <% Application Language"C#&…

ReportLab 导出 PDF(页面布局)

ReportLab 导出 PDF&#xff08;文档创建&#xff09; ReportLab 导出 PDF&#xff08;页面布局&#xff09; ReportLab 导出 PDF&#xff08;图文表格) PLATYPUS - 页面布局和排版 1. 设计目标2. 开始3. Flowables3.1. Flowable.draw()3.2. Flowable.drawOn(canvas,x,y)3.3. F…

Ubuntu下安装Intel MKL完整指南

&#x1f9e0; Intel MKL 安装指南&#xff08;Ubuntu 完整版&#xff09; 适用平台&#xff1a;Ubuntu 18.04 / 20.04 / 22.04 更新时间&#xff1a;2025 年最新版&#xff08;适配 Intel oneAPI 2024&#xff09; ✅ 一、安装方式选择 安装方式适合用户群体特点推荐程度&…

HackMyVM Gigachad.

Gigachad 信息搜集 ┌──(root㉿kali)-[/home/kali] └─# nmap 192.168.214.85 Starting Nmap 7.95 ( https://nmap.org ) at 2025-04-16 07:42 EDT Nmap scan report for 192.168.214.85 Host is up (0.00011s latency). Not shown: 997 closed tcp ports (reset) PORT S…