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

Mysql与Ooracle 索引失效场景对比

        MySQL 和 Oracle 作为主流关系型数据库,其索引失效的场景既有共性,也因底层优化器、索引类型支持等差异存在不同。以下从常见索引失效场景对比两者的表现及原因:

一、索引列上使用函数 / 表达式

  • 共性:若直接在索引列上使用函数或表达式(如SUBSTR(name, 1, 3)age + 1),优化器通常无法利用索引,导致失效。

    • 例:WHERE SUBSTR(name, 1, 3) = 'abc'name为索引列),两者均可能失效。
  • 差异

    • MySQL:在 8.0 版本前不支持 “函数索引”,此类场景必然失效;8.0 后支持函数索引(需显式创建,如CREATE INDEX idx_func ON t (SUBSTR(name, 1, 3))),创建后可避免失效。
    • Oracle:原生支持 “函数索引”(如CREATE INDEX idx_func ON t (SUBSTR(name, 1, 3))),若查询中的函数与索引定义一致,可正常使用索引,否则失效。

二、OR 连接的条件中存在无索引列

  • 共性:若OR连接的多个条件中,存在某列未建索引,优化器可能放弃使用索引(因需同时扫描索引和非索引列,效率可能低于全表扫描)。

  • 差异

    • MySQL:对OR的处理较严格。即使OR两边的列都有索引,也可能因优化器判断成本较高而失效(尤其当索引选择性低时)。例如:WHERE age = 20 OR name = 'abc'(两列均有索引),可能仍走全表扫描。
    • Oracle:优化器对OR的兼容性更好。若OR两边的列均有索引,通常会使用索引合并(Index Merge)策略,避免全表扫描。

三、否定操作符(!=、<>、NOT IN、IS NOT NULL)

  • 共性:此类操作符可能导致索引失效,因优化器认为扫描范围较大,全表扫描更高效。

  • 差异

    • MySQL!=NOT INIS NOT NULL几乎必然导致索引失效(仅当索引列值分布极不均匀时可能例外)。例如:WHERE age != 20age有索引),通常走全表扫描。
    • Oracle:处理更灵活。若索引列值稀疏(如大部分为NULL,查询IS NOT NULL),或NOT IN的范围极小,可能仍使用索引(但效率较低)。

四、隐式类型转换

  • 共性:当索引列类型与查询条件值类型不匹配时,数据库会自动进行类型转换(如字符串列name用数字123查询),导致索引失效。
    • 例:WHERE name = 123nameVARCHAR类型),两者均会失效(因转换为WHERE CAST(name AS UNSIGNED) = 123,等价于函数操作)。

五、模糊查询(LIKE)

  • 共性:以%开头的模糊查询(如LIKE '%abc'),索引通常失效(因无法通过索引前缀定位);以常量开头的查询(如LIKE 'abc%'),可能使用索引。

  • 差异

    • MySQLLIKE 'abc%'仅当索引列是字符串类型且无其他复杂条件时,才会使用索引;若结合其他条件(如AND age > 20),可能失效。
    • OracleLIKE 'abc%'对 B 树索引的支持更稳定,即使结合其他简单条件,也更可能使用索引(优化器对范围扫描的判断更灵活)。

六、联合索引违反 “最左前缀原则”

  • 共性:联合索引(如(a, b, c))需满足 “最左前缀”(查询条件包含a,或a + b,或a + b + c),否则失效。

    • 例:联合索引(a, b),查询WHERE b = 10,两者均失效。
  • 差异

    • MySQL:若联合索引中左侧列有 “范围查询”(如a > 10),则右侧列的索引失效(如WHERE a > 10 AND b = 20,仅a的索引有效,b失效)。
    • Oracle:优化器可能对范围查询后的列进行 “跳跃扫描”(Index Skip Scan),尤其当左侧列的基数(不同值数量)较小时(如a只有 2 个值),即使a用范围查询,b仍可能使用索引。

七、数据量极小或索引选择性低

  • 共性:当表数据量极小(如 <1000 行),或索引列选择性极低(如性别列,只有 “男 / 女”),优化器会认为全表扫描比索引扫描更快,主动忽略索引。

  • 差异

    • MySQL:对 “小表” 的判断更激进,即使表有几万行,若索引选择性低(如重复值占比 > 50%),也可能放弃索引。
    • Oracle:优化器对索引选择性的判断更精细,会结合统计信息(如直方图)评估成本,选择性略低时仍可能使用索引。

总结:核心差异点

场景MySQL 特点Oracle 特点
函数索引支持8.0 后支持,需显式创建原生支持,可直接适配查询中的函数
OR 条件处理严格,易失效,索引合并较少灵活,索引合并较常见
否定操作符几乎必然失效部分场景(如稀疏数据)可能使用索引
联合索引范围查询范围后列索引失效可能支持跳跃扫描,范围后列仍可用索引

实际开发中,需结合数据库类型、版本及执行计划(EXPLAIN/EXPLAIN PLAN)判断索引是否生效,避免依赖经验主义。

http://www.lryc.cn/news/614450.html

相关文章:

  • 大语言模型提示工程与应用
  • Node.js 》》数据验证 Joi 、express-joi
  • HarmonyOS SDK助力讯飞听见App能力建设
  • node.js 学习笔记2 进程/线程、fs
  • 力扣-56.合并区间
  • 经常问的14000
  • 智能巡检机器人的进化:当传统巡检遇上Deepoc具身智能外拓开发板
  • Visual Studio 2019 + Qt + MySQL 开发调试全过程问题详解
  • Vue 3 表单数据缓存架构设计:从问题到解决方案
  • 前端基础之《Vue(29)—Vue3 路由V4》
  • ADB打印设备日志相关
  • 手机拍照识别中模糊场景准确率↑37%:陌讯动态适配算法实战解析
  • 用LaTeX优化FPGA开发:结合符号计算与Vivado工具链(二)
  • 大模型量化上溢及下溢解析
  • ESP32-menuconfig(4) -- Partition Table
  • Web Worker 性能革命:让浏览器多线程为您的应用加速
  • ChipCamp探索系列 -- 1. Soft-Core RISC-V on FPGA
  • 【10】C#实战篇——C# 调用 C++ dll(C++ 导出函数、C++导出类)
  • 华清远见25072班C语言学习day5
  • Advances and Challenges in Foundation Agents--Memory调研
  • WPF 双击行为实现详解:DoubleClickBehavior 源码分析与实战指南
  • 基于ffmpeg和rk3588的mpp编解码库多路融屏程序设计
  • 贝叶斯定理 vs 条件概率
  • Redis(⑤-线程池隔离)
  • 【从0到1制作一块STM32开发板】6. PCB布线--信号部分
  • React函数组件灵魂搭档:useEffect深度通关指南!
  • 如何实现在多跳UDP传输场景,保证单文件和多文件完整传输的成功率?
  • 三相交流电机旋转磁场产生原理
  • Django模型开发全解析:字段、元数据与继承的实战指南
  • Flutter开发 多孩子布局组件