BETWEEN 子句与 <= AND >=

问题描述 投票:0回答:8

使用 BETWEEN 子句或使用 <= AND >= 比较之间是否存在性能差异?

即这两个查询:

SELECT *  
  FROM table  
 WHERE year BETWEEN '2005' AND '2010';  

...和

SELECT *  
  FROM table  
 WHERE year >= '2005' AND year <= '2010';

在此示例中,年份列是 VARCHAR2(4),其上有索引。

sql performance oracle oracle10g oracle11g
8个回答
35
投票

没有什么区别。

请注意,

BETWEEN
始终是包容性的并且对参数的顺序敏感。

BETWEEN '2010' AND '2005'
永远不会是
TRUE


26
投票

两个示例查询之间没有性能差异,因为

BETWEEN
只是表达 inclusive 范围比较的简写方式。当 Oracle 解析
BETWEEN
条件时,它会自动扩展为单独的比较子句:

例如。

SELECT *  
  FROM table
 WHERE column BETWEEN :lower_bound AND :upper_bound  

...会自动变成:

SELECT *  
  FROM table
 WHERE :lower_bound <= column
   AND :upper_bound >= column

可以通过检查解释计划来验证此行为。在这种情况下,两个查询将生成相同的解释计划,并且都将显示用于过滤结果的相同表达式:

Predicate Information (identified by operation id):
---------------------------------------------------
 
   1 - filter("YEAR"<='2010' AND "YEAR">='2005')

6
投票

实际上这取决于您的 DBMS 引擎。

某些数据库管理系统会计算两次您的表达式(每次比较一次),并且在您使用

BETWEEN
时仅计算一次。

实际上,如果表达式可以具有非确定性结果

BETWEEN
将会有不同的行为,请在 SQLite 中比较以下内容:

WHERE RANDOM() BETWEEN x AND y -- one random value generated

WHERE RANDOM() >= x AND RANDOM() <= y -- two distinct random values generated

如果您的表达式是(例如)子查询,这可能会非常耗时。


3
投票

当有疑问时(无论如何对于 Oracle),运行一个 解释计划,您将看到优化器想要做什么。 这适用于大多数有关“...之间是否存在性能差异”的问题。 当然还有很多其他工具,但解释计划是一个好的开始。


1
投票

应该是一样的。

好的数据库引擎将为该表达式生成相同的计划。


1
投票

可能值得考虑一下 SQL 标准(尽管这可能不对应于所有实现,即使它应该):

Format

<between predicate> ::=
  <row value constructor> [ NOT ] BETWEEN
    <row value constructor> AND <row value constructor>

Syntax Rules

[...]

6) "X BETWEEN Y AND Z" is equivalent to "X>=Y AND X<=Z".

话虽如此,行为上没有差异,尽管对于复杂的

X
,解析时间可能存在差异,正如 Benoit 这里提到的那样

发现于http://www.contrib.andrew.cmu.edu/~shadow/sql/sql1992.txt


0
投票

run1“X>=Y 和 X<=Z"

run2“Y 和 Z 之间的 X”

当我运行解释计划两次时,我得到一个

Plan hash value
。 但是 Tom 的 runStats_pkg 得到不同的结果:

Run1 ran in 1 cpu hsecs
Run2 ran in 1 cpu hsecs
run 1 ran in 100% of the time

Name                      Run1    Run2        Diff
STAT...recursive calls          12      13       1
STAT...CPU used by this sessio       2       3       1
STAT...physical read total IO        0       1       1
STAT...consistent gets          18      19       1
...
...
LATCH.row cache objects         44,375   1,121     -43,254
LATCH.cache buffers chains      68,814   1,397     -67,417
STAT...logical read bytes from     655,360     573,440     -81,920
STAT...session uga memory max      123,512       0    -123,512
STAT...session pga memory      262,144  65,536    -196,608
STAT...session pga memory max      262,144  65,536    -196,608
STAT...session uga memory     -327,440  65,488     392,928

Run1 latches total versus runs -- difference and pct
Run1        Run2    Diff       Pct
203,927      28,673    -175,254    711.22%

0
投票

您最好检查您的执行计划,因为可能存在一些奇怪的边缘情况,其中

BETWEEN
可能具有与标准 >= 和 <= combination.

不同的执行计划

https://blog.pythian.com/oracle-can- Between-and-greater-than-or-equal-to-and-less-than-or-equal-to-differ/

买者自负显然。但由于执行计划可能会随着时间的推移而改变,而且我真的没有兴趣测试这些东西,所以我根本不使用 BETWEEN。

有时选择越少越好。

© www.soinside.com 2019 - 2024. All rights reserved.