AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / dba / 问题 / 2918
Accepted
Jérôme Verstrynge
Jérôme Verstrynge
Asked: 2011-05-24 17:09:51 +0800 CST2011-05-24 17:09:51 +0800 CST 2011-05-24 17:09:51 +0800 CST

关于单线程与多线程数据库性能

  • 772

H2 是一个单线程数据库,在性能方面享有盛誉。其他数据库是多线程的。

我的问题是:什么时候多线程数据库比单线程数据库更有趣?有多少用户?有多少进程?触发器是什么?有人有经验可以分享吗?

概括

  • 通常的瓶颈是磁盘访问
  • SSD 速度快,但很脆弱(必须进行故障处理)
  • 单线程系统上的一个长查询将阻塞所有其他查询
  • 配置多线程系统可能很棘手
  • 即使在单核系统上,多线程数据库也是有益的
database-recommendation performance
  • 6 6 个回答
  • 81844 Views

6 个回答

  • Voted
  1. RolandoMySQLDBA
    2011-05-26T19:47:03+08:002011-05-26T19:47:03+08:00

    关于 MySQL,如果我能说一件事,那就是 InnoDB,它的事务(ACID 兼容)存储引擎,确实是多线程的。但是,它与您配置的一样多线程!!!即使是“开箱即用”,InnoDB 在默认设置下在单 CPU 环境中也表现出色。要利用 InnoDB 多线程功能,您必须记住激活很多选项。

    innodb_thread_concurrency设置 InnoDB 可以保持打开的并发线程数的上限。为此设置的最佳整数是(2 X CPU 数量)+ 磁盘数量。更新:正如我从 Percona NYC 会议中了解到的那样,您应该将其设置为 0,以提醒 InnoDB 存储引擎为其运行的环境找到最佳线程数。

    innodb_concurrency_tickets设置可以不受惩罚地绕过并发检查的线程数。达到该限制后,线程并发检查再次成为常态。

    innodb_commit_concurrency设置可以提交的并发事务数。由于默认值为 0,因此不设置它允许同时提交任意数量的事务。

    innodb_thread_sleep_delay设置 InnoDB 线程在重新进入 InnoDB 队列之前可以休眠的毫秒数。默认值为 10000(10 秒)。

    innodb_read_io_threads和innodb_write_io_threads(都从 MySQL 5.1.38 开始)为读取和写入分配指定数量的线程。默认值为 4,最大值为 64。

    innodb_replication_delay对从属设备施加线程延迟,达到 innodb_thread_concurrency。

    innodb_read_ahead_threshold允许在切换到异步读取之前线性读取设置的范围数(64 页 [page = 16K])。

    如果我指定更多选项,时间就会逃脱。您可以在MySQL 的文档中阅读它们。

    大多数人不知道这些功能,并且对 InnoDB 仅执行符合 ACID 的事务非常满意。如果您调整这些选项中的任何一个,则后果自负。

    我玩过 MySQL 5.5 多个缓冲池实例(9 个缓冲池实例中的 162GB),并试图以这种方式在内存中自动分区数据。一些专家说,这应该会给你 50% 的性能提升。我得到的是大量线程锁定,实际上使 InnoDB 爬行。我切换到 1 个缓冲区(162GB),世界上一切都好起来了。我想您需要 Percona 专家来设置它。我明天将参加在纽约举行的 Percona MySQL 会议,如果有机会,我会询问这个问题。

    总之,考虑到多线程操作的默认设置,InnoDB 现在在多 CPU 服务器中表现良好。调整它们需要非常小心、非常耐心、大量文档和优质咖啡(或 Red Bull、Jolt 等)。

    早安,晚安,晚安!!!

    更新 2011-05-27 20:11

    周四从纽约 Percona MySQL 会议回来。什么会议。学到了很多,但我得到了一个关于 InnoDB 的答案。Ronald Bradford告诉我,将 innodb_thread_concurrency 设置为 0 将使 InnoDB 在内部决定线程并发的最佳行动方案。我将在 MySQL 5.5 中进一步试验。

    更新 2011-06-01 11:20

    就一个长查询而言,InnoDB 是ACID 兼容的,并且使用MultiVersion Concurrency Control运行良好。事务应该能够携带隔离级别(默认情况下可重复读取),以防止阻止其他人访问数据。

    至于多核系统,InnoDB 已经走过了漫长的道路。过去,InnoDB 在多核环境中表现不佳。我记得必须在单个服务器上运行多个 mysql 实例才能让多个内核在 CPU 上分配多个 mysqld 进程。由于 Percona 和后来的 MySQL(嗯,Oracle,说这仍然让我作呕),这不再是必要的,因为他们已经将 InnoDB 开发成一个更成熟的存储引擎,可以简单地访问核心而无需太多调整。今天的 InnoDB 实例可以在单个核心服务器上运行良好。

    • 50
  2. Best Answer
    StanleyJohns
    2011-05-27T07:41:23+08:002011-05-27T07:41:23+08:00

    以下是我的看法:

    通常数据库系统的瓶颈(或最慢的部分)是磁盘。CPU 仅在算术运算、处理或 CPU 执行的任何其他任务期间出现峰值。通过适当的架构,多线程可以帮助抵消 CPU 上的查询负载,而不是进行缓慢的磁盘读/写。在某些情况下,使用 CPU 周期计算值比创建计算列(先前保存到磁盘)并从磁盘读取该列更快。

    在某些 RDBMS 中有一个临时 DB (tempdb),该实例上的所有 DB 都使用它来进行排序、散列、临时变量等。多线程和拆分此 tempdb 文件可用于提高 tempdb 的吞吐量,从而提高整体服务器性能。

    使用多线程(并行性),查询的结果集可以拆分为在服务器的不同内核上进行处理,而不是单独使用一个内核。此功能并不总能提高性能,但在某些情况下确实如此,因此该功能可用。

    DB 可用的线程有多种用途:读/写磁盘、用户连接、后台作业、锁定/闩锁、网络 IO 等......根据操作系统架构,线程被抢先馈送到 CPU 并且是使用等待和队列进行管理。如果 CPU 可以很快地处理这些线程,那么等待时间就会很短。多线程数据库将比单线程数据库更快,因为在单线程数据库中,将只回收一个线程而不是让其他线程可用的开销。

    可扩展性也成为一个问题,因为需要更多线程来管理和执行扩展的数据库系统。

    • 33
  3. Luke Hutteman
    2011-05-25T08:55:52+08:002011-05-25T08:55:52+08:00

    只要您有多个并发用户或进程,甚至是具有多线程数据库访问的单个进程,拥有一个支持线程的数据库就会变得有趣。

    H2 是线程安全的,但是对数据库的所有请求都进行了序列化,这在重负载场景下可能会成为潜在的性能问题。对于特定项目是否确实如此,取决于您的性能要求、访问数据库的线程/用户/进程的数量、这些线程执行的查询频率以及您的平均和最差情况下的性能。查询。

    例如,如果你的性能要求是在一秒钟内得到响应,你有不超过 10 个并发用户执行一个需要 0.05 秒执行的查询,单线程数据库仍然可以让你达到这些目标(尽管多线程可能已经显着提升了性能)。考虑到与单个潜在查询相同的场景,但最坏情况下性能为半秒,序列化数据库访问将不再让您满足性能目标。

    如果您当前在您的项目中使用 H2,我建议您在负载情况下针对您的代码库运行分析器(只需使用一些典型的用例启动 x 数量的线程同时访问您的代码)。这将为您提供有关代码库中性能和瓶颈的实际指标,而不仅仅是理论化。如果这表明您的请求大部分时间都在等待访问数据库,那么是时候转移到线程数据库了。

    • 11
  4. Jack Douglas
    2011-05-27T11:17:39+08:002011-05-27T11:17:39+08:00

    据我所知,“单线程”对于 H2 来说有点用词不当。关键是它序列化所有事务(即一次只做一个)。

    关于您的应用程序是否“可以”的关键问题不是“有多少用户?” 甚至是“有多少进程?”,而是“我的交易需要多长时间?”

    如果您的所有交易都在亚秒以下,那可能没问题,如果有些交易需要几个小时才能完成,那可能就不行了,因为所有其他待处理的交易都在等待它们完成。关于这是否“好”的决定将取决于您自己的性能要求 - 即我的用户使用事务访问数据库的可接受等待时间。

    - 编辑

    似乎 H2 并没有真正序列化事务 - 只是 DML。换句话说,单个长事务中的大量短更新不会阻塞其他更新。但是,除非您使用实验性 MVCC 功能,否则表锁定意味着这在实践中具有类似的效果。还有一个实验性的“多线程”功能,但不能与 MVCC 同时使用

    • 8
  5. Denis de Bernardy
    2011-05-29T07:12:16+08:002011-05-29T07:12:16+08:00

    引用 PostgreSQL 网站上的点点滴滴……请注意,我完全不知道这些论点的优点——它们只是不适合发表评论。

    来自开发人员常见问题解答(“为什么不使用线程......”):

    http://wiki.postgresql.org/wiki/Developer_FAQ#Why_don.27t_you_use_threads.2C_raw_devices.2C_async-I.2FO.2C_.3Cinsert_your_favorite_wizz-bang_feature_here.3E.3F

    当前不使用线程来代替后端的多个进程,因为:(...)

    • 如果它们是单个进程中的线程,则一个后端中的错误可能会破坏其他后端
    • 与剩余的后端启动时间相比,使用线程的速度改进很小。
    • 共享只读可执行映射和使用 shared_buffers 意味着进程(如线程)非常节省内存
    • 定期创建和销毁进程有助于防止内存碎片,这在长时间运行的进程中可能难以管理

    从待办事项列表(“我们不想要的功能”)中:

    http://wiki.postgresql.org/wiki/Todo#Features_We_Do_Not_Want

    所有后端在单个进程中作为线程运行(不需要)

    这消除了我们从当前设置中获得的过程保护。线程创建通常与现代系统上的进程创建开销相同,因此使用纯线程模型似乎是不明智的,并且 MySQL 和 DB2 已经证明线程引入的问题与它们解决的问题一样多。(...)

    所以,再次......我完全不知道上述的优点。只是太长了,无法发表评论。

    • 5
  6. oazabir
    2011-05-25T08:14:06+08:002011-05-25T08:14:06+08:00

    只有当您有超过 1 个并行查询进入数据库时​​,多线程数据库才会使您受益。这取决于您拥有的用户数量。如果您有超过 10 个用户同时在应用程序上工作,他们很可能会同时在数据库上生成多个查询。

    此外,多线程数据库只有在 CPU 上有多核时才能受益。如果有单核,多线程数据库必须将作业排队并在单核上顺序执行。当有多核时,每个核可以并行运行一个线程。从而获得更好的性能。

    这是否回答了您的问题?

    • -3

相关问题

  • 推荐使用哪些数据库作为嵌入式数据库?

  • 您如何针对繁重的 InnoDB 工作负载调整 MySQL?

  • 如何确定是否需要或需要索引

  • 我在哪里可以找到mysql慢日志?

  • 如何优化大型数据库的 mysqldump?

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    你如何mysqldump特定的表?

    • 4 个回答
  • Marko Smith

    您如何显示在 Oracle 数据库上执行的 SQL?

    • 2 个回答
  • Marko Smith

    如何选择每组的第一行?

    • 6 个回答
  • Marko Smith

    使用 psql 列出数据库权限

    • 10 个回答
  • Marko Smith

    我可以查看在 SQL Server 数据库上运行的历史查询吗?

    • 6 个回答
  • Marko Smith

    如何在 PostgreSQL 中使用 currval() 来获取最后插入的 id?

    • 10 个回答
  • Marko Smith

    如何在 Mac OS X 上运行 psql?

    • 11 个回答
  • Marko Smith

    如何从 PostgreSQL 中的选择查询中将值插入表中?

    • 4 个回答
  • Marko Smith

    如何使用 psql 列出所有数据库和表?

    • 7 个回答
  • Marko Smith

    将数组参数传递给存储过程

    • 12 个回答
  • Martin Hope
    Manuel Leduc PostgreSQL 多列唯一约束和 NULL 值 2011-12-28 01:10:21 +0800 CST
  • Martin Hope
    markdorison 你如何mysqldump特定的表? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    Stuart Blackler 什么时候应该将主键声明为非聚集的? 2011-11-11 13:31:59 +0800 CST
  • Martin Hope
    pedrosanta 使用 psql 列出数据库权限 2011-08-04 11:01:21 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 对 SQL 查询进行计时? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas 如何从 PostgreSQL 中的选择查询中将值插入表中? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 列出所有数据库和表? 2011-02-18 00:45:49 +0800 CST
  • Martin Hope
    BrunoLM Guid vs INT - 哪个更好作为主键? 2011-01-05 23:46:34 +0800 CST
  • Martin Hope
    bernd_k 什么时候应该使用唯一约束而不是唯一索引? 2011-01-05 02:32:27 +0800 CST
  • Martin Hope
    Patrick 如何优化大型数据库的 mysqldump? 2011-01-04 13:13:48 +0800 CST

热门标签

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve