我有一个 Drupal 安装访问一个大型用户数据库(~200k 行),我的“人员查找器”功能需要访问所有这些行(以随机顺序)。我似乎无法在 Drupal 的 UI 中使用LIMIT和使用OFFSET(并且我在 Drupal 视图中使用大型数据集进行慢查询时在 Drupal.SE 上有一个与 Drupal 特定的问题略有不同- 更适合在 SQL 或 PHP 中处理?,哪个解决了这个问题,以及这个问题的一部分),但我的特定于 mySQL 的问题如下:
我需要根据另一个表中的数据排除一些行(“包括角色 A 中所有不在角色 B、C 或 D 中的用户)。Drupal 生成的查询是有效的
SELECT
users.uid AS uid,
/* some columns */,
RAND() AS random_field
FROM
users users
INNER JOIN users_roles users_roles ON users.uid = users_roles.uid
LEFT JOIN users_roles users_roles2
ON users.uid = users_roles2.uid
AND (users_roles2.rid = :views_join_condition_0
OR users_roles2.rid = :views_join_condition_1 …Run Code Online (Sandbox Code Playgroud) 我可以理解,如果我加入“单独快速”的单个查询,组合可能会变慢,因为默认执行计划可能不是最佳的。但是,当我知道一个查询的行数非常少时,我想我应该能够使用提示来控制连接。
select cj.a, cv.b
from (select distinct a from complexJoin) cj -- 2 rows
inner loop join complexView cv
on cj.a = cv.a
order by cj.a, cv.b
Run Code Online (Sandbox Code Playgroud)
如果 cj <1s 和 cv <1s 期望这是 <~2s 但使用任何提示(合并/散列/循环)通常> 1分钟。
我还尝试使用 CROSS APPLY,因为文档声称内部选择对于每个外部行只执行一次。该查询比手动运行两次内部查询需要大约 100 倍的时间,所以也许我不理解文档。
select cj.a, cv.b
from (select distinct a from complexJoin) cj -- 2 rows
cross apply (select * from complexView
where a = cj.a) cv
order by cj.a, cv.b
Run Code Online (Sandbox Code Playgroud)
如果我用“cj”的结果填充临时表,然后加入 _with_no_hint_ 或使用交叉应用,它会很快,但我真的必须求助于它吗?如果我使用临时表并尝试“任何”连接提示(循环/合并/散列),它会很慢,所以这可能是一个关键点。
我不相信深入查询计划的深度(两者都是复杂的开始)是解决一般问题所必需的:我只想保证隔离而不诉诸临时表 - 这真的不可能?
我的问题:
我正在尝试与一个表中的数据子集进行比较,并且我有两种方法可以部分工作,并且确定必须有一种更正确的方法来做到这一点。
这里的想法是一个包含关于同一系统随时间推移的数据集的表格,我想比较它们,特别是看看何时有介绍或缺席。请允许我用一个简单的测试表来演示:
mysql> select * from gocore;
+-----+------------+------+----------+----------+
| uid | server | tag | software | revision |
+-----+------------+------+----------+----------+
| 1 | enterprise | old | apache | 2.2.25 |
| 2 | enterprise | new | apache | 2.4.6 |
| 3 | enterprise | new | tomcat | 7.0.42 |
| 4 | enterprise | old | geronimo | 2.1.7 |
+-----+------------+------+----------+----------+
Run Code Online (Sandbox Code Playgroud)
在这个例子中有两个数据集——标签“旧”数据集和标签“新”数据集。每个都反映了在某个时间点采集的数据样本。对于服务器“企业”,我们有一个随时间变化的软件包(apache)、一个引入的软件包(tomcat)和一个消失的软件包(geronimo)。
我的目标:一个可以让我总结“旧”和“新”之间状态的查询:
+------------+----------+----------+----------+
| server | software | revision | revision |
+------------+----------+----------+----------+ …Run Code Online (Sandbox Code Playgroud) 我有两个疑问:
第一个如下:
SELECT *
FROM batch bp
INNER JOIN sender_log sl ON sl.id=bp.log_id
AND bp.protocol='someprotocol'
Run Code Online (Sandbox Code Playgroud)
第二个查询用于删除行:
delete from batch where protocol='someprotocol'
Run Code Online (Sandbox Code Playgroud)
我知道在 postgres 中我们有RETURNING *来返回已删除的行。我想要实现的是删除行并在一个查询中返回它们。我怎样才能做到这一点?
我有以下架构:
CREATE TABLE Person (
PersonId int PRIMARY KEY
)
CREATE TABLE Action (
ActionId int PRIMARY KEY,
PersonId int NOT NULL FOREIGN KEY REFERENCES Person(PersonId),
ActionTime datetime NOT NULL
)
Run Code Online (Sandbox Code Playgroud)
以及以下数据:
INSERT INTO Person (PersonId) VALUES
(1),
(2),
(3),
(4)
INSERT INTO Action (ActionId, PersonId, ActionTime) VALUES
(1, 1, '2014-02-01'),
(2, 1, '2014-02-02'),
(3, 2, '2014-02-02'),
(4, 3, '2014-03-05')
Run Code Online (Sandbox Code Playgroud)
我想运行一个查询,显示每个人在每个月的 15 日之间执行的操作数。例如,我正在尝试以下操作:
SELECT
Person.PersonId,
COALESCE(GroupA_Actions_Made, 0) AS GroupA_Actions_Made,
COALESCE(GroupB_Actions_Made, 0) AS GroupB_Actions_Made
FROM
Person
RIGHT OUTER JOIN (
SELECT …Run Code Online (Sandbox Code Playgroud) 我在 SQL Server 数据库中有两张表,一张有两列,一张有四列:
tbl_email_list
email_list_id int (PK)email_list_name varchartbl_email-details
email_uniq_id int (PK)email_list_id int (FK)email_address varcharblacklist bit我想在一个应该返回的查询中检索数据
+----+-----------+-----------+-------------+----------+
| id | value_id | parent_id | dropdown_id | name |
+----+-----------+-----------+-------------+----------+
| 7 | 14945 | 14944 | 57 |4000 |
| 8 | 14944 | 0 | 56 |bbb |
| 9 | 14943 | 14940 | 59 |comprable |
| 10 | 14942 | 14939 | 59 |comprable |
| 11 | 14940 | 14931 | 58 |3 |
| 12 | 14939 | 14930 | 58 |2 |
| 13 | 14931 | 14929 | …Run Code Online (Sandbox Code Playgroud) 我有 2 个表:tbl1、tbl2。
CREATE TABLE tbl1(time_1)
AS VALUES
( '2017-09-06 15:26:03'::timestamp ),
( '2017-09-06 15:26:02' ),
( '2017-09-06 15:28:01' ),
( '2017-09-06 15:40:00' );
CREATE TABLE tbl2(time_2)
AS VALUES
( '2017-09-06 15:29:01'::timestamp ),
( '2017-09-06 15:40:00' ),
( '2017-09-06 15:23:59' ),
( '2017-09-06 15:45:58' );
Run Code Online (Sandbox Code Playgroud)
我想加入表格,因此对于 tbl1 中的每一行都匹配 tbl2 中最接近的时间。输出是:
time_1 time_2
--------------------- --------------------
2017-09-06 15:26:03 2017-09-06 15:23:59
2017-09-06 15:26:02 2017-09-06 15:23:59
2017-09-06 15:28:01 2017-09-06 15:29:01
2017-09-06 15:40:00 2017-09-06 15:45:58
Run Code Online (Sandbox Code Playgroud)
我知道如何找到最近时间的单个值:
SELECT * from tbl1 where time_1=INPUT_TIME ORDER BY case …Run Code Online (Sandbox Code Playgroud) 我有一个关于这个查询计划的问题。
我们在测试环境中有一个表 Order_Details_Taxes,它有 11,225,799 行。该表有一个列 OrdTax_PLTax_LoadDtl_Key,它在每一行上都是 NULL。此测试环境的配置方式使此列始终为 NULL。此列上有一个索引。
我使用列的 NULL 值对该表运行了一些查询。NULL INNER JOIN 永远不会产生任何结果。
declare @Keys table (KeyValue decimal(15,0))
insert into @Keys (KeyValue) values (null)
select OrdTax_PLTax_LoadDtl_Key
from @Keys
inner join Order_Details_Taxes
on OrdTax_PLTax_LoadDtl_Key = KeyValue
select *
from @Keys
inner join Order_Details_Taxes
on OrdTax_PLTax_LoadDtl_Key = KeyValue
Run Code Online (Sandbox Code Playgroud)
这些是查询计划中的第一个查询。第一个select从亿行表开始并连接到@Keys。第二个select从@Keys 开始,但它对这个表进行聚集索引扫描。
我知道在大多数情况下临时@Tables 是有问题的,所以我将查询更改为使用临时 #Table:
if object_id ('tempdb..#Keys') is not null
drop table #Keys
create table #Keys (KeyValue decimal(15,0))
insert into #Keys (KeyValue) values (null)
select OrdTax_PLTax_LoadDtl_Key …Run Code Online (Sandbox Code Playgroud) 简介: 我有一个简单的数据库模式,但即使只有几十条记录,基本查询的性能也已经成为一个问题。
数据库:PostgreSQL 9.6
简化架构:
CREATE TABLE article (
id bigint PRIMARY KEY,
title text NOT NULL,
score int NOT NULL
);
CREATE TABLE tag (
id bigint PRIMARY KEY,
name text NOT NULL
);
CREATE TABLE article_tag (
article_id bigint NOT NULL REFERENCES article (id),
tag_id bigint NOT NULL REFERENCES tag (id),
PRIMARY KEY (article_id, tag_id)
);
CREATE INDEX ON article (score);
Run Code Online (Sandbox Code Playgroud)
生产数据信息:
所有表都是读/写的。写入量低,每几分钟左右只有一个新记录。
大概记录数:
每篇文章平均 5 个标签。
问题 …
join ×10
mysql ×3
postgresql ×3
sql-server ×3
performance ×2
count ×1
delete ×1
group-by ×1
hints ×1
merge ×1
null ×1
optimization ×1
paging ×1
select ×1
subquery ×1
time ×1
view ×1