《收获,不止Oracle》读书笔记之性能提升千倍

news2024/11/13 15:32:07

体系学习让SQL语句性能提升千倍

未优化前,单车速度

drop table t purge;
create table t(x int);

create or replace procedure proc1
as
begin
  for i in 1..100000
  loop
      execute immediate
      'insert into t values ('||i||')';
  commit;
  end loop;
end;
/
/*这里要记得预先执行一遍,将过程创建起来!*/

SQL> conn scott/tiger@PDB1
Connected.
SQL> 
SQL> drop table t purge;

Table dropped.

SQL> create table t(x int);

Table created.

SQL> conn system/system@PDB1;
Connected.
SQL> alter system flush shared_pool;

System altered.

SQL> conn scott/tiger@PDB1
Connected.
SQL> set timing on
SQL> exec proc1;

PL/SQL procedure successfully completed.

Elapsed: 00:01:08.95
SQL> select count(*) from t;

  COUNT(*)
----------
    100000

Elapsed: 00:00:00.05
SQL> 

首次实验68.95秒完成,仅是单车速度。

共享池中缓存下来的SQL语句以及hash出来的唯一值,都可以在v$sql中对应的sql_text和sql_id字段中查询到,而解析的次数和执行的次数分别可以从PARSE_CALLS和EXECUTIONS字段中获取。

由于这个过程proc1执行的是insert into t 的系列插入,于是我们执行如下语句来查询proc1在数据库共享池中执行的情况,具体如脚本,原来是因为未用绑定变量:

SQL> conn system/system@PDB1;
Connected.
SQL>
SQL> set pagesize 200
SQL> set linesize 200
SQL> select
  2  t.sql_text,t.sql_id,t.PARSE_CALLS,t.EXECUTIONS
  3  from v$sql t
  4  where sql_text like '%insert into t values%';

SQL_TEXT
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
SQL_ID                                  PARSE_CALLS EXECUTIONS
--------------------------------------- ----------- ----------
insert into t values (99995)
gqyu6ma5xw3py                                     1          1

insert into t values (99989)
2fn9gs19m43uc                                     1          1

insert into t values (99979)
23cu38akgwkv5                                     1          1

insert into t values (99994)
2vnmk62v3nmqa                                     1          1

insert into t values (99985)
dk8z68ns2nn0v                                     1          1

select t.sql_text,t.sql_id,t.PARSE_CALLS,t.EXECUTIONS from v$sql t where sql_text like '%insert into t values%'
frxh5v32hsrvn                                     2          2

insert into t values (99990)
441jb9gwj8vx1                                     1          1

insert into t values (99978)
2tq0v2xmqnwp6                                     1          1

insert into t values (99983)
f8tf9zkgx9153                                     1          1

insert into t values (99992)
cdg9816w1dbq9                                     1          1

insert into t values (99973)
8suj6myp2xhgf                                     1          1

insert into t values (99984)
brk4w33ad5mpr                                     1          1

insert into t values (99982)
fd7ubwctyduc9                                     1          1

insert into t values (100000)
g65kz1a5y1z3g                                     1          1

insert into t values (99980)
9z1r38t72jzb7                                     1          1

insert into t values (99987)
b05m5tng0a0p2                                     1          1

insert into t values (99975)
0tucc5wuwu5ag                                     1          1

insert into t values (99977)
aq8w8yyuxb0xx                                     1          1

insert into t values (99986)
bxncx5tr7m345                                     1          1

insert into t values (99999)
7t5qy2x3sr3jd                                     1          1

insert into t values (99998)
78pya7qqqg63x                                     1          1

insert into t values (99988)
0vjsduj05g684                                     1          1

insert into t values (99991)
6z00wthhvg87h                                     1          1

insert into t values (99974)
bda0639gcrcus                                     1          1

insert into t values (99997)
fcc6yrvnp7jqt                                     1          1

insert into t values (99996)
15jhq0cxsvkrh                                     1          1

insert into t values (99976)
bc9hd40jp3rrj                                     1          1

insert into t values (99981)
dtr9su4cnzsxh                                     1          1

insert into t values (99993)
8hbu4zqu2zxw5                                     1          1


29 rows selected.

Elapsed: 00:00:00.00
SQL> 

发现共享池中有大量的类似的SQL语句,而sql_id各自不同,每条语句都只解析1次,执行1次,解析了10万次,怪不得速度如此之慢。

2.绑定变量,摩托速度

第2次改进,将proc1改造成有绑定变量的proc2

create or replace procedure proc2
as
begin
  for i in 1..100000
  loop
      execute immediate
      'insert into t values (:x)' using i;
  commit;
  end loop;
end;
/
/*这里要记得预先执行一遍,将过程创建起来!*/

接下来我们继续测试proc2过程(注意,重建表的目的是为了公平,测试都在无记录的空表上进行,并且共享池都清空.

第2次改进后7秒完成,单车变摩托车

SQL> 
SQL> conn scott/tiger@PDB1
Connected.
SQL> drop table t purge;

Table dropped.

Elapsed: 00:00:00.27
SQL> create table t(x int);

Table created.

Elapsed: 00:00:00.03
SQL> 
SQL> conn system/system@PDB1;
Connected.
SQL> alter system flush shared_pool;

System altered.

Elapsed: 00:00:00.12
SQL> conn scott/tiger@PDB1
Connected.
SQL> set pagesize 200
SQL> set linesize 200
SQL> set timing on
SQL> exec proc2;

PL/SQL procedure successfully completed.

Elapsed: 00:00:07.03
SQL> select count(*) from t;

  COUNT(*)
----------
    100000

Elapsed: 00:00:00.01
SQL> 

 解析与执行次数

 

 虽然插入的语句值各不相同,但是都被绑定为:x,所以被hash成唯一一个hash值,名称为bbz6pdq577unj,很明显可以看出解析1次,执行10万次,这就是速度大幅度提升的原因了。

3.静态改写,汽车速度

execute immediate 是一种动态SQL写法,常用于表名和字段名是变量、入参的情况,由于表名都不知道,当然不能直接写SQL语句了,所以要靠动态SQL语句根据传入的表名参数来拼成一条SQL语句,由execute immediate调用执行。但这里显然不需要多此一举,因为insert into t values(i)完全可以满足需求,表名就是t。

第3此改进,将proc2改造成静态SQL的proc3

create or replace procedure proc3
as
begin
  for i in 1..100000
  loop
      insert into t values (i);
  commit;
  end loop;
end;
/
/*这里要记得预先执行一遍,将过程创建起来!*/

第3次改进后3秒完成,摩托变汽车

[oracle@oracle-db-19c ~]$ sqlplus / as sysdba                                  

SQL*Plus: Release 19.0.0.0.0 - Production on Tue Jan 3 13:19:12 2023
Version 19.3.0.0.0

Copyright (c) 1982, 2019, Oracle.  All rights reserved.


Connected to:
Oracle Database 19c Enterprise Edition Release 19.0.0.0.0 - Production
Version 19.3.0.0.0

SQL> set pagesize 200
SQL> set linesize 200
SQL> alter session set container=PDB1;

Session altered.

SQL> conn scott/tiger@PDB1;
Connected.
SQL> 
SQL> drop table t purge;

Table dropped.

SQL> create table t(x int);

Table created.

SQL> 
SQL> conn system/system@PDB1;
Connected.
SQL> alter system flush shared_pool;

System altered.

SQL>
SQL> conn scott/tiger@PDB1;
Connected.
SQL> set pagesize 200
SQL> set linesize 200
SQL> set timing on
SQL> exec proc3;

PL/SQL procedure successfully completed.

Elapsed: 00:00:03.83
SQL> select count(*) from t;

  COUNT(*)
----------
    100000

Elapsed: 00:00:00.03
SQL> 

静态SQL解析与执行次数

select t.sql_text, t.sql_id, t.PARSE_CALLS, t.EXECUTIONS
  from v$sql t
 where upper(sql_text) like '%INSERT INTO T VALUES%';

果然如此,proc3也实现了绑定变量,而且动态SQL的特点是执行过程中再解析,而静态SQL的特点是编译的过程就解析好了。这点差别就是速度再度提升的原因。

4.批量提交,动车速度

commit触发LGWR将Redo Buffer写出到Redo Log中,并且将回滚段的活动事务标记为不活动,同时在回滚段中记录对应前镜像记录的所在位置,并标记为可以重写,切记commit可不是写数据的动作哦,写数据将数据从Data Buffer刷出磁盘是由CKPT决定的。

第4次改进,将proc3改造成提交在循环外的proc4

create or replace procedure proc4
as
begin
  for i in 1..100000
  loop
      insert into t values (i);
  end loop;
    commit;
end;
/
/*这里要记得预先执行一遍,将过程创建起来!*/

第4次改进后1秒完成,汽车变动车

[oracle@oracle-db-19c ~]$ sqlplus / as sysdba

SQL*Plus: Release 19.0.0.0.0 - Production on Tue Jan 3 13:34:43 2023
Version 19.3.0.0.0

Copyright (c) 1982, 2019, Oracle.  All rights reserved.


Connected to:
Oracle Database 19c Enterprise Edition Release 19.0.0.0.0 - Production
Version 19.3.0.0.0

SQL> alter session set container=PDB1;

Session altered.

SQL> conn scott/tiger@PDB1;
Connected.
SQL> set pagesize 200
SQL> set linesize 200
SQL> 
SQL> drop table t purge;

Table dropped.

SQL> create table t (x int);

Table created.

SQL> 
SQL> conn system/system@PDB1;
Connected.
SQL> alter system flush shared_pool;

System altered.

SQL> conn scott/tiger@PDB1;
Connected.
SQL> set pagesize 200
SQL> set linesize 200
SQL> set timing on
SQL> exec proc4;

PL/SQL procedure successfully completed.

Elapsed: 00:00:01.57
SQL> select count(*) from t;

  COUNT(*)
----------
    100000

Elapsed: 00:00:00.00
SQL> 



5.集合写法,飞机速度

将1到10万记录依次插入到t表中,完全满足刚才的需求,不过这种写法大家可能略感陌生,结果却是对的。

insert into t select rownum from dual connect by level<=100000;

第5次用集合写法后0.25秒完成,动车变飞机。

[oracle@oracle-db-19c ~]$ sqlplus / as sysdba

SQL*Plus: Release 19.0.0.0.0 - Production on Tue Jan 3 13:41:05 2023
Version 19.3.0.0.0

Copyright (c) 1982, 2019, Oracle.  All rights reserved.


Connected to:
Oracle Database 19c Enterprise Edition Release 19.0.0.0.0 - Production
Version 19.3.0.0.0

SQL> alter session set container=PDB1;

Session altered.

SQL> conn scott/tiger@PDB1;
Connected.
SQL> set pagesize 200
SQL> set linesize 200
SQL> drop table t purge;

Table dropped.

SQL> create table t (x int);

Table created.

SQL> conn system/system@PDB1;
Connected.
SQL> alter system flush shared_pool;

System altered.

SQL> conn scott/tiger@PDB1;
Connected.
SQL> set pagesize 200
SQL> set linesize 200
SQL> set timing on
SQL> insert into t select rownum from dual connect by level<=100000;

100000 rows created.

Elapsed: 00:00:00.25
SQL> commit;

Commit complete.

Elapsed: 00:00:00.00
SQL> select count(*) from t;

  COUNT(*)
----------
    100000

Elapsed: 00:00:00.01
SQL> 

6.直接路径,火箭速度

实验准备,将集合写法的实验数据量放大100倍

 

7.并行设置,飞船速度

 首先请大家自行从 Oracle 官方网站下载 CONCEPT 文档,并尽量在一周的时间内阅读完毕(可先不阅读其中指向的细节部分,那是自己选择性阅读的内容)

 

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

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

相关文章

linux下常用调试技巧

1 linux下如何查看静态库和动态库都链接了那些库 1.1 静态库.a是没有指令可以看到其在生成过程中链接了那些库的 1.2 动态库.so可以通过ldd指令查看其在生成过程中链接了那些库 还有一种简单直观的方法,我们可以在编译过程中看到所生成的二进制文件,链接了那些库: 平时编译…

[阶段4 企业开发进阶] 7. 微服务--SpringCloud Alibaba

文章目录1 服务注册和配置中心Nacos1.1 Nacos简介1.2 Nacos作为服务注册中心服务提供者注册服务消费者注册和负载服务注册中心对比1.3 Nacos作为服务配置中心基础配置分类配置DataID方案配置Group方案配置Namespace方案配置1.4 Nacos集群和持久化配置2 服务熔断和限流SentinelS…

指针仪表读数识别系统 yolov7

指针仪表读数识别系统通过 yolov7opencv计算机视觉分析技术,利用现场摄像头可以自动识别指针型仪表读数并将读数回传给平台节省人工巡检读表的时间。YOLOv7 在 5 FPS 到 160 FPS 范围内&#xff0c;速度和精度都超过了所有已知的目标检测器&#xff0c;并在V100 上&#xff0c;…

【日常系列】LeetCode《24·贪心1》

数据规模->时间复杂度 <10^4 &#x1f62e;(n^2) <10^7:o(nlogn) <10^8:o(n) 10^8<:o(logn),o(1) 内容 lc 455 &#xff1a;分发饼干 - 贪心思想 https://leetcode.cn/problems/assign-cookies/ 提示&#xff1a; 1 < g.length < 3 * 10^4 0 < s.len…

配置双网卡聚合

一 服务器多网卡聚合的意义 1、多网卡聚合&#xff0c;可以起到网络链路冗余作用&#xff0c;当故障发生时&#xff0c;网络自动切换&#xff0c;保证业务数据不中断。 2、多网卡聚合成一条虚拟链路&#xff0c;可实现网络带宽提升&#xff0c;如2个1000Mbps的网卡聚合&#…

【收藏】使用Google Colab随时随地运行Python代码

Colab官网 什么是 Colab? Colab,或“Colaboratory”,允许您在浏览器中编写和执行 Python,不需要依赖本地资源。具有以下优势: 需要零配置免费使用GPU轻松分享几大非常方便的特性: 和Google Drive无缝融合 可以将文件存储在Google Drive里面,同时也可以从Google Driv…

TiDB性能调优

文章目录一、 TiDB 常见配置优化1.1 限制 SQL 内存使用和执行时间1.1.1 执行时间限制1.1.2 内存使用限制1.2 事务重试设置1.3 Join 算子优化1.4 常见 Mysql 兼容问题1.5 其他优化项二、TiKV优化2.1 TiKV 线程池优化2.1.1 GRPC2.1.2 Scheduler2.1.3 Raftstore2.1.4 UnifyReadPoo…

对象存储服务MinIO

1. MinIO简介 对象存储的方式对比 分布式文件系统 MinIO概述: 1.MinIO基于Apache License v2.0开源协议的对象存储服务&#xff0c;可以做为云存储的解决方案用来保存海量的图片&#xff0c;视频&#xff0c;文档。 2.Golang语言实现&#xff0c;配置简单&#xff0c;单行命令…

学习css3,使用代码实现一根心爱的二踢脚

2023春节快到了&#xff0c;虽然还在上班&#xff0c;但心情早已开始激动&#xff0c;感叹2022终将过去&#xff0c;喜迎2023兔年吧。让我以激动的心情&#xff0c;利用所学css3代码知识&#xff0c;实现一根心爱的二踢脚吧。 目录 1、实现思路 2、实现二踢脚的主体圆柱部分…

数据的存储(1)数据类型,整型在内存中的存储

TIPS 1. 函数递归必须存在限制条件。 2. 一维数组与二维数组在内存当中是连续存放的&#xff0c;二维数组的话反正也是一行一行往下走。如果能知道起始地址的话&#xff0c;后面顺藤摸瓜会很容易。 3. 数组越界的话&#xff0c;C语言本身是不做检查的。数组传参传的是数组首…

【跟学C++】面向对象三大特征——继承(Study20)

文章目录1、了解继承2、基类与派生类(父类与子类)2.1、概念2.2、案例展示3、构造顺序与析构顺序4、继承种类4.1、私有继承4.2、保护继承4.3、多继承5、总结 【说明】 大家好&#xff0c;本专栏主要是跟学C内容&#xff0c;自己学习了这位博主【 AI菌】的【C21天养成计划】&…

十五、类加载器、反射

类加载器 1类加载器【理解】 作用 负责将.class文件&#xff08;存储的物理文件&#xff09;加载在到内存中 2类加载的过程【理解】 类加载时机 创建类的实例&#xff08;对象&#xff09;调用类的类方法访问类或者接口的类变量&#xff0c;或者为该类变量赋值使用反射方式来…

excel制表基础:规范的制表理念和思路让效率提升 下篇

在日常工作中我们会构建很多的表格&#xff0c;其实这些表格无论多少&#xff0c;都可以归结为三大类&#xff0c;分别为“源数据表”、“关系信息表”和“统计分析表”。上次我们提到了一套表格“统计的核心”——“源数据表”&#xff0c;今天继续为大家分享“关系信息表”和…

力扣(LeetCode)1802. 有界数组中指定下标处的最大值(C++)

贪心二分查找 贪心性质&#xff1a;对于数组中确定位置index的数&#xff0c;要使nums[index]最大&#xff0c;等于使得整个数组之和最小。 提示 &#xff1a;数组相邻元素之差的绝对值小于1&#xff0c;为了数组之和最小&#xff0c;从index往左&#xff0c;形成公差为1的递减…

python实现多张多格式图片转PDF并打包成exe

目录 主要思路 转PDF初始代码 转PDF最终代码 GUI界面设计代码 打包成可执行文件 完整代码 附录 主要思路 从文件夹中读取图片数据&#xff0c;然后将他们保存为PDF格式。 转PDF初始代码 不长&#xff0c;大概10行代码。 from PIL import Image from os import *def …

Stardust 案例:制作散景光斑

本文介绍使用 Ae 插件 Stardust 制作散景光斑的一般方法与步骤。效果视频1、新建合成。持续时间&#xff1a;10 秒。2、新建纯色图层&#xff0c;命名为“散景光斑”&#xff0c;然后添加 Stardust 效果。3、设置 Emitter&#xff08;发射器&#xff09; 。用一个长方形的发射器…

2023外贸人出国抢单攻略(附带2023年全球重要展会)

自11月底以来&#xff0c;全国陆续传来政府带团出国抢单的消息&#xff0c;让沉寂了3年之久的外贸行业热情高涨。这不仅预示着3年抗疫斗争的胜利&#xff0c;更意味着中国三驾马车之一的外贸行业开启了高速运转的车轮。“浙江带领万家企业去欧洲抢单&#xff01;”“福建省商务…

少儿Python每日一题(10):手机键盘

原题解答 本次的题目如下所示(原题出处:NOC) 一般的手机的键盘是这样的: 要按出英文字母就必须要按数字键多下。例如要按出 x 就得按 9 两下,第一下会出 w,而第二下会把 w 变成 x。0 键按一下会出一个空格。 你的任务是读取若干句只包含英文小写字母和空格的句子,求出要…

装备制造业ERP软件如何帮助企业做好物料齐套管理?

在生产制造过程中&#xff0c;要想提高生产效率&#xff0c;齐套管理是很重要的一环&#xff0c;会直接影响库存、交付和效率。而装备制造行业原料种类特别多&#xff0c;通用件也非常多&#xff0c;齐套检查工作十分复杂&#xff0c;深受以下问题困扰&#xff1a;1.装备制造业…

springmvc源码之HandlerMapping处理器映射器

系列文章目录 springmvc源码之Web上下文初始化 springmvc源码之DispatcherServlet前端控制器 springmvc源码之HandlerMapping处理器映射器 文章目录系列文章目录HandlerMapping处理器映射器实现类配置mvc:annotation-driven配置的作用RequestMappingHandlerMapping源码创建访问…