sudo-iのBlog

  • 🍟首页
  • 🍊目录
    • 技术分享
    • vps教程
    • 软件分享
    • 干货分享
  • 🍎链接
  • 🍓工具
    • 🌽IP路由追踪
    • 域名被墙检测
    • KMS激活
    • 域名whois查询
  • 🍕联系
  • 🍌登录
Sudo-i
关注互联网,生活,音乐,乐此不疲
  1. 首页
  2. 干货分享
  3. 正文

数据库优化技巧:提升查询性能的 10 个实战方法

4 3 月, 2026 73点热度 0人点赞 0条评论

# 数据库优化技巧:提升查询性能的 10 个实战方法

在软件开发中,数据库性能往往是系统瓶颈的关键所在。今天分享 10 个经过实战验证的数据库优化技巧,帮助你显著提升查询性能。

## 1. 合理使用索引

索引是数据库优化的第一道防线。但索引并非越多越好,需要遵循以下原则:

```sql
-- ✅ 好的索引:针对高频查询字段
CREATE INDEX idx_user_email ON users(email);
CREATE INDEX idx_order_created ON orders(created_at, status);

-- ❌ 避免:对低基数字段单独建索引
CREATE INDEX idx_gender ON users(gender); -- 只有男/女两个值
```

**复合索引的最左前缀原则**:
```sql
-- 索引:(last_name, first_name, age)
SELECT * FROM users WHERE last_name = "张"; -- ✅ 使用索引
SELECT * FROM users WHERE last_name = "张" AND first_name = "三"; -- ✅ 使用索引
SELECT * FROM users WHERE first_name = "三"; -- ❌ 不使用索引
```

## 2. 优化 SELECT 语句

避免 SELECT *,只查询需要的字段:

```sql
-- ❌ 不推荐
SELECT * FROM users WHERE status = 1;

-- ✅ 推荐
SELECT id, name, email FROM users WHERE status = 1;
```

**好处**:
- 减少网络传输数据量
- 提高缓存命中率
- 避免回表查询

## 3. 使用 EXPLAIN 分析查询

```sql
EXPLAIN SELECT u.name, o.total
FROM users u
JOIN orders o ON u.id = o.user_id
WHERE o.created_at > "2026-01-01";
```

**关注要点**:
- `type`:至少达到 `range` 级别,理想是 `ref` 或 `const`
- `key`:实际使用的索引
- `rows`:扫描的行数,越少越好
- `Extra`:避免出现 `Using filesort` 或 `Using temporary`

## 4. 避免 N+1 查询问题

```python
# ❌ 糟糕的写法:N+1 查询
users = User.query.all()
for user in users:
orders = Order.query.filter_by(user_id=user.id).all()
# 产生了 N+1 次查询

# ✅ 优化:使用 JOIN 或预加载
users = User.query.options(joinedload(User.orders)).all()
# 只产生 2 次查询
```

## 5. 合理使用分页

深分页会严重拖慢查询:

```sql
-- ❌ 深分页:扫描前 100000 行丢弃
SELECT * FROM orders ORDER BY created_at DESC LIMIT 100000, 20;

-- ✅ 优化:使用游标分页
SELECT * FROM orders
WHERE created_at < "2026-01-01 00:00:00" ORDER BY created_at DESC LIMIT 20; ``` ## 6. 批量操作代替循环插入 ```python # ❌ 低效:逐条插入 for item in items: db.execute("INSERT INTO logs VALUES (...)" ) # ✅ 高效:批量插入 db.execute("INSERT INTO logs VALUES (...), (...), (...)") # 或使用 executemany db.executemany("INSERT INTO logs VALUES (...)", items) ``` ## 7. 优化 JOIN 操作 ```sql -- ✅ 确保 JOIN 字段有索引 SELECT u.name, o.total FROM users u INNER JOIN orders o ON u.id = o.user_id -- user_id 应有索引 WHERE u.status = 1; -- ✅ 小表驱动大表 SELECT * FROM large_table l INNER JOIN small_table s ON l.id = s.large_id; -- small_table 驱动 ``` ## 8. 使用覆盖索引 覆盖索引可以避免回表,显著提升性能: ```sql -- 创建覆盖索引 CREATE INDEX idx_status_created ON orders(status, created_at, total); -- 查询只使用索引中的数据 SELECT status, created_at, total FROM orders WHERE status = "completed"; -- ✅ 不需要回表查询 ``` ## 9. 避免在 WHERE 中对字段进行函数操作 ```sql -- ❌ 索引失效 SELECT * FROM orders WHERE DATE(created_at) = "2026-03-03"; SELECT * FROM users WHERE UPPER(name) = "张三"; -- ✅ 保持索引有效 SELECT * FROM orders WHERE created_at >= "2026-03-03 00:00:00"
AND created_at < "2026-03-04 00:00:00"; ``` ## 10. 定期维护数据库 ```sql -- 分析表统计信息 ANALYZE TABLE orders; -- 优化表(整理碎片) OPTIMIZE TABLE orders; -- 检查慢查询 SHOW PROCESSLIST; SELECT * FROM mysql.slow_log; ``` ## 性能对比示例 | 优化项 | 优化前 | 优化后 | 提升 | |--------|--------|--------|------| | 无索引查询 | 2.5s | 0.05s | 50 倍 | | SELECT * | 1.2s | 0.3s | 4 倍 | | N+1 查询 | 5.0s | 0.2s | 25 倍 | | 深分页 | 3.8s | 0.1s | 38 倍 | ## 总结 数据库优化是一个持续的过程。建议: 1. **监控先行**:开启慢查询日志,定期分析 2. **逐步优化**:先解决最慢的查询 3. **测试验证**:优化前后对比 EXPLAIN 结果 4. **文档记录**:记录优化方案和效果 记住:没有银弹,只有适合你业务场景的最优解。 --- *本文首发于炫影博客,转载请注明出处。*

无关联文章

本作品采用 知识共享署名 4.0 国际许可协议 进行许可
标签: 暂无
最后更新:4 3 月, 2026

李炫炫

这个人很懒,什么都没留下

点赞
< 上一篇
下一篇 >

文章评论

razz evil exclaim smile redface biggrin eek confused idea lol mad twisted rolleyes wink cool arrow neutral cry mrgreen drooling persevering
取消回复

COPYRIGHT © 2025 sudo-iのBlog. ALL RIGHTS RESERVED.

Theme Kratos Made By Seaton Jiang

鲁ICP备2024054662号

鲁公网安备37108102000450号