MySQL中between子句和limit子句的区别解析
<div id="navCategory"><h5 class="catalogue">目录</h5><ul class="first_class_ul"><li><a href="#_label0">一、核心区别(一句话)</a></li><li><a href="#_label1">二、语义层面的本质区别</a></li><ul class="second_class_ul"><li><a href="#_lab2_1_0">1. BETWEEN(范围条件)</a></li><li><a href="#_lab2_1_1">2. LIMIT(数量限制)</a></li></ul><li><a href="#_label2">三、执行顺序上的区别(非常关键)</a></li><ul class="second_class_ul"></ul><li><a href="#_label3">四、索引利用上的差异(性能重点)</a></li><ul class="second_class_ul"><li><a href="#_lab2_3_2">1. BETWEEN 与索引</a></li><li><a href="#_lab2_3_3">2. LIMIT 与索引</a></li></ul><li><a href="#_label4">五、BETWEEN + LIMIT联合使用(高频实战)</a></li><ul class="second_class_ul"></ul><li><a href="#_label5">六、典型使用场景对比</a></li><ul class="second_class_ul"></ul><li><a href="#_label6">七、一个非常常见的误区</a></li><ul class="second_class_ul"><li><a href="#_lab2_6_4">误区:LIMIT 可以代替 BETWEEN</a></li></ul><li><a href="#_label7">八、性能相关的延伸</a></li><ul class="second_class_ul"></ul><li><a href="#_label8">九、对比总结表</a></li><ul class="second_class_ul"></ul></ul></div><p class="maodian"><a name="_label0"></a></p><h2>一、核心区别(一句话)</h2><blockquote><p><code>BETWEEN</code> 用来“限定数据的取值范围”,属于过滤条件;<br /><code>LIMIT</code> 用来“限定返回的行数”,属于结果裁剪。</p></blockquote>
<p>两者<strong>解决的问题不同</strong>,不能互相替代。</p>
<p class="maodian"><a name="_label1"></a></p><h2>二、语义层面的本质区别</h2>
<p class="maodian"><a name="_lab2_1_0"></a></p><h3>1. BETWEEN(范围条件)</h3>
<div class="jb51code"><pre class="brush:sql;">WHERE id BETWEEN 10 AND 20</pre></div>
<p>含义:</p>
<ul><li>按 <strong>列的取值范围</strong> 过滤数据</li><li><strong>左右边界都包含</strong>(闭区间)</li><li>属于 <code>WHERE</code> 条件的一部分</li></ul>
<p>等价写法:</p>
<div class="jb51code"><pre class="brush:sql;">WHERE id >= 10 AND id <= 20</pre></div>
<p class="maodian"><a name="_lab2_1_1"></a></p><h3>2. LIMIT(数量限制)</h3>
<div class="jb51code"><pre class="brush:sql;">LIMIT 10
LIMIT 10 OFFSET 20</pre></div>
<p>含义:</p>
<ul><li>不关心值是什么</li><li>只限制<strong>返回多少行</strong></li><li>在结果集生成后再裁剪</li><li>如果存在偏移量,从指定的偏移量开始查询的位置</li></ul>
<p class="maodian"><a name="_label2"></a></p><h2>三、执行顺序上的区别(非常关键)</h2>
<p>SQL 的逻辑执行顺序(简化):</p>
<div class="jb51code"><pre class="brush:sql;">FROM
→ WHERE ← BETWEEN 在这里生效
→ ORDER BY
→ LIMIT ← LIMIT 在这里生效</pre></div>
<p><strong>结论:</strong></p>
<ul><li><code>BETWEEN</code> 影响 <strong>参与计算的行</strong></li><li><code>LIMIT</code> 只影响 <strong>最终返回的行数</strong></li></ul>
<p class="maodian"><a name="_label3"></a></p><h2>四、索引利用上的差异(性能重点)</h2>
<p class="maodian"><a name="_lab2_3_2"></a></p><h3>1. BETWEEN 与索引</h3>
<div class="jb51code"><pre class="brush:sql;">SELECT * FROM user WHERE id BETWEEN 100 AND 200;</pre></div>
<ul><li><code>id</code> 是主键 / 有索引</li><li>使用 <strong>B+Tree 范围扫描</strong></li><li>从第一个匹配值开始,顺着叶子链表扫描</li><li><strong>高效</strong></li></ul>
<p class="maodian"><a name="_lab2_3_3"></a></p><h3>2. LIMIT 与索引</h3>
<div class="jb51code"><pre class="brush:sql;">SELECT * FROM user ORDER BY id LIMIT 10;</pre></div>
<ul><li>如果 <code>ORDER BY id</code> 有索引</li><li>可以顺序扫描索引前 10 行</li><li>同样高效</li></ul>
<p>但:</p>
<div class="jb51code"><pre class="brush:sql;">SELECT * FROM user LIMIT 10;</pre></div>
<ul><li>无排序语义</li><li>返回结果不稳定</li><li>通常仍需扫描</li></ul>
<p class="maodian"><a name="_label4"></a></p><h2>五、BETWEEN + LIMIT联合使用(高频实战)</h2>
<div class="jb51code"><pre class="brush:sql;">SELECT *
FROM user
WHERE id BETWEEN 100 AND 10000
ORDER BY id
LIMIT 10;</pre></div>
<p>执行逻辑:</p>
<ul><li>使用主键索引定位到 <code>id = 100</code></li><li>顺序扫描</li><li><strong>扫描到 10 行后立即停止</strong></li></ul>
<p>这是<strong>高性能分页/截断查询</strong>的典型写法。</p>
<p class="maodian"><a name="_label5"></a></p><h2>六、典型使用场景对比</h2>
<table><thead><tr><th>场景</th><th>适合 BETWEEN</th><th>适合 LIMIT</th></tr></thead><tbody><tr><td>按数值区间筛选</td><td>是</td><td>否</td></tr><tr><td>时间范围查询</td><td>是</td><td>否</td></tr><tr><td>只取前 N 条</td><td>否</td><td>是</td></tr><tr><td>分页查询</td><td>否</td><td>是</td></tr><tr><td>大表范围扫描</td><td>是</td><td>否</td></tr><tr><td>防止返回过多数据</td><td>否</td><td>是</td></tr></tbody></table>
<p class="maodian"><a name="_label6"></a></p><h2>七、一个非常常见的误区</h2>
<p class="maodian"><a name="_lab2_6_4"></a></p><h3>误区:LIMIT 可以代替 BETWEEN</h3>
<p>假如要查找最新插入的100条数据</p>
<div class="jb51code"><pre class="brush:sql;">-- 错误理解
SELECT * FROM orders LIMIT 100;</pre></div>
<p>问题:</p>
<ul><li>不保证是“最新 100 条”</li><li>不保证顺序</li></ul>
<p><strong>正确写法:</strong></p>
<div class="jb51code"><pre class="brush:sql;">SELECT *
FROM orders
ORDER BY created_at
LIMIT 100;</pre></div>
<p class="maodian"><a name="_label7"></a></p><h2>八、性能相关的延伸</h2>
<ul><li><code>BETWEEN</code> 是 <strong>过滤条件</strong>,减少扫描行数</li><li><code>LIMIT</code> 是 <strong>短路机制</strong>,减少返回行数</li><li><strong>二者配合,性能最好</strong></li><li>深分页场景中:</li></ul>
<div class="jb51code"><pre class="brush:sql;">LIMIT 100000, 10</pre></div>
<ul><li>性能很差,应改为 <strong>基于索引的范围分页</strong></li></ul>
<p class="maodian"><a name="_label8"></a></p><h2>九、对比总结表</h2>
<table><thead><tr><th>对比维度</th><th>BETWEEN</th><th>LIMIT</th></tr></thead><tbody><tr><td>作用</td><td>限定值范围</td><td>限定行数</td></tr><tr><td>所属子句</td><td>WHERE</td><td>结果阶段</td></tr><tr><td>是否过滤数据</td><td>是</td><td>否</td></tr><tr><td>是否依赖索引</td><td>是(强)</td><td>否(弱)</td></tr><tr><td>是否影响扫描范围</td><td>是</td><td>否</td></tr></tbody></table>
頁:
[1]