首页 > 数据库 >OB_MYSQL UPDATE 优化案例

OB_MYSQL UPDATE 优化案例

时间:2024-06-18 16:10:27浏览次数:13  
标签:COOP SERVICE NO WHERE UPDATE CONTRACT OB MYSQL TYPE

在工单系统上看到有一条SQL问题还没解决,直接联系这位同学看看是否需要帮忙。

 

慢SQL:

UPDATE  A
SET CORPORATION_NAME = (
    SELECT DISTINCT CORPORATION_NAME
    FROM (
        SELECT CONTRACT_NO, 
               COOP_SERVICE_TYPE, 
               CORPORATION_NAME, 
               PROJECT_NAME, 
               ROW_NUMBER() OVER (PARTITION BY CONTRACT_NO, COOP_SERVICE_TYPE ) AS SEQ
        FROM O_PLIS_PROC B
        WHERE B.BDHA_TX_DATE='2024-06-10' AND A.LM_CT1_NO = B.CONTRACT_NO
    ) B
    WHERE B.COOP_SERVICE_TYPE='01' AND B.SEQ = 1
)
WHERE LM_CT1_NO IN (
    SELECT  CONTRACT_NO
    FROM O_PLIS_PROC C
    WHERE C.CONTRACT_NO=A.LM_CT1_NO
    AND C.COOP_SERVICE_TYPE='01'
    AND C.BDHA_TX_DATE='2024-06-10'
);

执行计划:

上面sql 跑超时都跑不出结果,估计要执行非常长时间。

这条sql in 后面关联返回107911行数据,update set ... 可以理解成标量子查询,返回1107911数据相当于 update set 标量子查询也要执行107911次。

 标量子查询最重要的是要走对索引,然而这个sql计划根本没走索引,这位同学的问题也是如何通过改写来消除标量子查询,很明显这个思路是错误的。

添加合适的索引:

CREATE INDEX TEST ON O_PLIS_PROC(
  BDHA_TX_DATE,
  COOP_SERVICE_TYPE,
  CONTRACT_NO,
  COOP_SERVICE_TYPE,
  CORPORATION_NAME);

很明显,创建索引以后计划显示能用上索引,sql整体5秒能执行完成。

 

再提供个相同逻辑的等价改写方案:

WITH O_PLIS_PROC as (
    SELECT 
           CONTRACT_NO,
           COOP_SERVICE_TYPE,
           CORPORATION_NAME
     FROM O_PLIS_PROC 
     WHERE BDHA_TX_DATE='2024-06-10' AND COOP_SERVICE_TYPE='01'
)
UPDATE A
SET CORPORATION_NAME = (
    SELECT  CORPORATION_NAME 
        FROM O_PLIS_PROC B 
    WHERE A.LM_CT1_NO = B.CONTRACT_NO  GROUP BY CONTRACT_NO, COOP_SERVICE_TYPE LIMIT 1 ) 
WHERE LM_CT1_NO IN (
    SELECT  CONTRACT_NO
    FROM O_PLIS_PROC C
    WHERE C.CONTRACT_NO=A.LM_CT1_NO
);

改写后的sql 5秒能跑出结果,和原来逻辑一样,提升不大。

 

遇到性能慢的sql语句,不要一上来就想着等价改写,先通过索引进行优化,合理的索引能解决90%的性能问题。

如果索引都解决不了的情况下,才去尝试使用等价改写来进行优化sql,一般来说等价改写能解决剩下5%的问题。

如果连等价改写都解决不了剩下的5%的性能问题话,就要尝试改业务,或者改数据库技术栈来解决问题了,这种通常来说成本会非常高。 

标签:COOP,SERVICE,NO,WHERE,UPDATE,CONTRACT,OB,MYSQL,TYPE
From: https://www.cnblogs.com/yuzhijian/p/18254499

相关文章

  • MySQL基础
    数据库基础知识数据库基础概念(1)数据库(Database,简称DB):数据库是存放数据的仓库,是长期储存在计算机内、有组织有结构的、可共享的数据集合。(2)数据库管理系统(DatabaseManagementSystem,简称DBMS):数据库管理系统是为数据库的建立、使用和维护而配置的数据库管理软件,它位于用户与......
  • Objective-C — static关键字用法详解
    Static的作用在Objective-C中,static关键字有几种不同的用途,主要用于修饰全局变量、局部变量、修饰静态函数1、static修饰的静态全局变量代码#import<Foundation/Foundation.h>//由于静态变量作用域仅限于声明它的文件,所以访问和设置可以通过以下方法来访问//通过setGlob......
  • MySQL动态权限详解
    MySQL数据库系统在管理用户访问控制时,除了传统的静态权限之外,还引入了动态权限的概念。动态权限机制为系统管理员提供了更为灵活和细致的权限管理方式,允许根据运行时环境和特定组件的需求来定义和授予权限。本文将深入探讨MySQL动态权限的特性和应用方法。动态权限的基本概念......
  • 【MySQL】复合查询和内外连接
    文章目录MySQL复合查询和内外连接1.复合查询1.1多表查询1.2自连接1.3子查询单行子查询多行子查询多列子查询from中使用子查询合并查询2.内外连接1.INNERJOIN2.LEFTJOIN3.RIGHTJOIN4.FULLJOIN5.CROSSJOINMySQL复合查询和内外连接1.复合查询1.1......
  • javascript-obfuscator混淆
    安装npminstalljavascript-obfuscator-g配置重度混淆,性能低性能下降50-100%{"compact":true,"controlFlowFlattening":true,"controlFlowFlatteningThreshold":0.75,//设置为0到1之间的值"deadCodeInjection":tr......
  • MySQL:创建账户及修改密码
    1、创建账户MySQL5.8:grantallprivilegeson*.*totst@%identifiedby'123456';MySQL8.0:createuser'tst'@'%'identifiedby'123456';grantallprivilegeson*.*to'tst'@'%'withgrantoption;......
  • mysql数据库名带下划线等特殊字符时,分权限报错
    原文链接:mysql数据库名带下划线分权限报错_mob64ca12f24f3a的技术博客_51CTO博客 MySQL数据库名带下划线分权限报错解析在使用MySQL进行数据库操作时,我们经常会遇到数据库名带下划线导致权限报错的情况。这是因为MySQL对于数据库名中的下划线有特殊的处理机制,容易导致权限控制......
  • MySQL入门学习.子查询.IN
        IN子查询是MySQL中一种常见的子查询类型,用于在查询中确定一个值是否在另一个查询的结果集中。IN子查询的特点是简洁明了,它可以在一个查询中方便地检查一个值是否在一组值中,非常适用于需要进行条件验证或关联查询的情况。   在MySQL中,有以下几种常见的......
  • MySQL入门学习-子查询.EXISTS
        子查询EXISTS是MySQL中的一种子查询类型,用于检查子查询结果集是否为空。如果子查询结果集不为空,则EXISTS子查询返回TRUE;否则,返回FALSE。    子查询EXISTS的特点是它只关心子查询结果集是否为空,而不关心结果集中的具体内容。这使得EXISTS子查......
  • Ragas实践问题记录2 AttributeError: ‘TestsetGenerator‘ object has no attribute
    报错问题依然是在尝试官方文档“CompareLLMsusingRagasEvaluations”的“Createsynthetictestdata”步骤发生报错。官方文档以及文档中代码如下:Ragas:CompareLLMsusingRagasEvaluations官方文档中的代码:importosfromllama_indeximportdownload_loader,Simp......