标签: optimization

大量插入的 InnoDB 表不会使用我所有的 CPU

我有一个几乎从不查询的数据包日志数据库。它只需要快速插入即可。我使用 InnoDB 是因为我想保持 ACID 合规性,因为即使丢失一个数据包也可能对我们的客户造成损害。在性能调优方案中,我通过多个数据库连接向服务器发送 1,000,000 个数据包。但是无论我在 my.cnf 中使用什么设置,我都无法让 mysqld 进程在 12 核的系统上使用超过 900% 的 CPU。(盒子上没有其他东西在运行。)

我设置了以下内容

  • innodb_file_per_table = 1
  • innodb_write_io_threads = 64
  • innodb_read_io_threads = 64
  • innodb_thread_concurrency = 0

如果我使用 MyISAM,我可以在大约 6 秒内写入所有数据包。但是 InnoDB 大约需要 25。我可以让 MySQL 使用剩余的系统资源并更快地插入吗?

编辑:这是表的架构:

+-------+----------------------+------+-----+---------+-------+
| Field | Type                 | Null | Key | Default | Extra |
+-------+----------------------+------+-----+---------+-------+
| t     | bigint(20) unsigned  | YES  |     | NULL    |       |
| a     | char(1)              | YES  |     | NULL    |       |
| sa    | …
Run Code Online (Sandbox Code Playgroud)

mysql innodb myisam optimization mysql-5.5

8
推荐指数
1
解决办法
3589
查看次数

如何加速 MySQL 上的“显示列”?

我的应用程序依赖于为某些表运行“显示列”。运行大约需要 60 毫秒,而我们所有其他查询都需要不到 1 毫秒。information_schema直接查询甚至更慢。

该数据库包含约250个数据库,每个数据库有100到200张表(总共约2万张表)。

  • 我怎样才能找出为什么这些操作这么慢?
  • 也许我可以更改一些设置以使其运行得更快,或者在 SQL 端缓存它?

(该应用程序每页加载执行大约 14 个这样的查询 - 我很清楚需要清理这个遗留代码,但在我进行长期修复时寻找可能的选项。)

mysql performance optimization

8
推荐指数
1
解决办法
6878
查看次数

为瞬态数据优化 PostgreSQL

我有几个表,每个表有 100-300 列整数类型,它们保存高度易变的数据。数据集由一两个主键作为键,刷新时删除整个数据集,并在一个事务中插入新数据。数据集大小通常是几百行,但在极端情况下可以达到几千行。每秒刷新一次,不同键的数据集更新通常是脱节的,因此删除和重新创建表是不可行的。

我如何调整 Postgres 来处理这样的负载?如果这有什么不同,我可以使用最新和最好的版本。

postgresql optimization database-tuning

8
推荐指数
1
解决办法
1613
查看次数

使用 JOIN 有效地更新表

我有一张表,其中包含家庭的详细信息,而另一个表则包含与这些家庭相关的所有人员的详细信息。对于家庭表,我使用其中的两列定义了一个主键 - [tempId,n]。对于 person 表,我有一个使用其 3 列定义的主键[tempId,n,sporder]

使用主键上的聚集索引所指示的排序,我为每个家庭[HHID]和每个人的[PERID]记录生成了一个唯一 ID (下面的代码片段用于生成 PERID]:

 ALTER TABLE dbo.persons
 ADD PERID INT IDENTITY
 CONSTRAINT [UQ dbo.persons HHID] UNIQUE;
Run Code Online (Sandbox Code Playgroud)

现在,我的下一步是将每个人与相应的家庭相关联,即;将 a 映射[PERID]到 a [HHID]。两个表之间的人行横道基于两列[tempId,n]。为此,我有以下内部连接语句。

UPDATE t1
  SET t1.HHID = t2.HHID
  FROM dbo.persons AS t1
  INNER JOIN dbo.households AS t2
  ON t1.tempId = t2.tempId AND t1.n = t2.n;
Run Code Online (Sandbox Code Playgroud)

我总共有1928783个户籍记录和5239842个人记录。执行时间目前非常高。

现在,我的问题:

  1. 是否可以进一步优化此查询?更一般地说,优化连接查询的拇指规则是什么?
  2. 是否有另一个查询构造可以以更好的执行时间实现我想要的结果?

我已将SQL Server 2008 为整个脚本生成的执行计划上传到 SQLPerformance.com

join sql-server optimization execution-plan

8
推荐指数
1
解决办法
1万
查看次数

如何优化各种类型的 MySQL 查询索引

我有一个 INNODB 表levels

+--------------------+--------------+------+-----+ -------+-------+
| 领域 | 类型 | 空 | 钥匙 | 默认 | 额外 |
+--------------------+--------------+------+-----+ -------+-------+
| 身份证 | 整数(9) | 否 | PRI | 空 | |
| 级别名称 | varchar(20) | 否 | | 空 | |
| 用户 ID | 整数(10) | 否 | | 空 | |
| 用户名 | varchar(45) | 否 | | 空 | |
| 评级 | 十进制(5,4) | 否 | | 0.0000 | |
| …

mysql innodb performance optimization index-tuning query-performance

8
推荐指数
1
解决办法
443
查看次数

为什么 SQL Server 为其限定的表的每一行运行一个子查询?

此查询在 ~21 秒内运行(执行计划):

select 
    a.month
    , count(*) 
from SubqueryTest a 
where a.year = (select max(b.year) from SubqueryTest b)
group by a.month
Run Code Online (Sandbox Code Playgroud)

当子查询被变量替换时,它会在 <1 秒内运行(执行计划):

declare @year float
select @year = max(b.year) from SubqueryTest b
select 
    month
    , count(*) 
from SubqueryTest where year = @year group by month
Run Code Online (Sandbox Code Playgroud)

从执行计划来看,“select max...”子选择对“SubqueryTest a:”中的数百万行中的每一行都运行,这就是为什么它需要这么长时间。

我的问题:由于子选择是标量、确定性且不相关,为什么查询优化器不执行我在第二个示例中所做的操作并运行子查询一次,存储结果,然后将其用于主查询?我确定我对 SQL Server 的理解只是一个漏洞,但我真的很想帮助填补它 - 用谷歌几个小时没有帮助。

该表刚超过 1GB,有近 2800 万条记录:

CREATE TABLE SubqueryTest(
  [pk_id] [int] IDENTITY(1,1) NOT NULL
  , [Year] [float] NULL
  , [Month] [float] NULL …
Run Code Online (Sandbox Code Playgroud)

optimization database-tuning sql-server-2008-r2 subquery

8
推荐指数
1
解决办法
9892
查看次数

使用 COALESCE(...) 优化子查询的选择

我有一个从应用程序中使用的大视图。我想我已经缩小了我的性能问题,但我不确定如何解决它。视图的简化版本如下所示:

SELECT ISNULL(SEId + '-' + PEId, '0-0') AS Id,
   *,
   DATEADD(minute, Duration, EventTime) AS EventEndTime
FROM (
    SELECT se.SEId, pe.PEId,
        COALESCE(pe.StaffName, se.StaffName) AS StaffName, -- << Problem!
        COALESCE(pe.EventTime, se.EventTime) AS EventTime,
        COALESCE(pe.EventType, se.EventType) AS EventType,
        COALESCE(pe.Duration, se.Duration) AS Duration,
        COALESCE(pe.Data, se.Data) AS Data,
        COALESCE(pe.Field, se.Field) AS Field,
        pe.ThisThing, se.OtherThing
    FROM PE pe FULL OUTER JOIN SE se 
      ON pe.StaffName = se.StaffName
     AND pe.Duration = se.Duration
     AND pe.EventTime = se.EventTime
    WHERE NOT(pe.ThisThing = 1 AND se.OtherThing = 0)
) Z …
Run Code Online (Sandbox Code Playgroud)

sql-server optimization t-sql subquery

8
推荐指数
1
解决办法
4416
查看次数

是否可以为不同/分组获得基于搜索的并行计划?

这个问题的一个例子表明,SQL Server 将选择全索引扫描来解决这样的查询:

select distinct [typeName] from [types]
Run Code Online (Sandbox Code Playgroud)

其中 [typeName] 有一个非聚集的、非唯一的升序索引。他的示例有 200M 行,但只有 76 个唯一值。在这种密度下,搜索计划似乎是更好的选择(约 76 次二进制搜索)?

他的情况可以正常化,但问题的原因是我真的想解决这样的问题:

select TransactionId, max(CreatedUtc) 
from TxLog 
group by TransactionId
Run Code Online (Sandbox Code Playgroud)

上有一个索引(TransactionId, MaxCreatedUtc)

使用标准化源 (dt) 重写不会改变计划。

select dt.TransactionId, MaxCreatedUtc
 from [Transaction] dt -- distinct transactions
 cross apply
   (
        select Max(CreatedUtc) as MaxCreatedUtc 
          from TxLog tl
         where tl.TransactionId = dt.TransactionId         
   ) ca
Run Code Online (Sandbox Code Playgroud)

仅将 CA 子查询作为标量 UDF 运行确实显示了 1 次搜索的计划。

select max(CreatedUtc) as MaxCreatedUtc
 from Pub.TransactionLog 
 where TransactionID = @TxId;
Run Code Online (Sandbox Code Playgroud)

在原始查询中使用该标量 UDF 似乎可行,但会失去并行性(UDF 的已知问题): …

index sql-server optimization group-by distinct

8
推荐指数
1
解决办法
415
查看次数

使用 WITH 构造的奇怪优化效果

我有 4 个表,让我们将它们命名为:

  1. 表 A,15M 行
  2. 表 B,40K 行,
  3. 表 C,30K 行,
  4. 表 D,25M 行

(kk - 表示数百万)

我有一个遗留查询,它是这样构造的:

select C.<some_fields>,B.<some_fields>,D.<some_fields> from C
inner join A on C.x = A.x
inner join D on D.z = 123 and D.a_id = A.a_id
inner join B on C.x = B.x and B.z = 123
where A.type = 'Xxx'
Run Code Online (Sandbox Code Playgroud)

此查询非常慢,执行结果最多需要 3 分钟(对于特定情况,它返回 35k 行)。

但是当我将其更改为以下结构时:

with t as (
   select C.<some_fields>,D.<some_fields> from C
   inner join A on C.x = A.x
   inner join D …
Run Code Online (Sandbox Code Playgroud)

postgresql performance optimization execution-plan amazon-rds query-performance

7
推荐指数
1
解决办法
166
查看次数

为什么 PostgreSQL 9.5 不使用我最新的 ORDER BY 索引,即使它使用类似的索引就好了?

(这篇文章的后续内容:当我在子查询中 ORDER BY 时,为什么我的 PostgreSQL 表达式索引没有被使用?

PostgreSQL 9.5。

我不能透露全部细节,但table有 22 列和 5 个索引:

  1. 主键 ('pk'), text(btree)
  2. 另一个text(btree)
  3. 一个timestamp with time zone(btree)
  4. 一个tsvector(杜松子酒)
  5. 我最新的一个bigint(btree)

(从上一篇文章你知道我试图避免创建这个额外的列,只是使用表达式索引——将两integer列加在一起——没有成功。bigint这里的列可能只是“整数”,但我做了一个创建它时出错;添加列、填充它并重新编制索引花了大约一个小时,所以我希望这不相关,但要提及它以防万一。)

除了tsvector.

以下查询都只需要 12ms 并且只使用一个Index Scan

  1. SELECT pk FROM table ORDER BY pk DESC LIMIT 10
  2. SELECT pk FROM table ORDER BY text_column DESC LIMIT 10
  3. SELECT pk FROM table ORDER BY timestamp_column DESC LIMIT 10 …

postgresql performance index optimization postgresql-9.5 postgresql-performance

7
推荐指数
1
解决办法
382
查看次数