Mysql:索引计数查询与维护汇总表

Mysql:索引计数查询与维护汇总表

问题描述:

我正在一个电子商务网站上,用户可以显示对可用产品的兴趣,并将其作为潜在客户存储在mysql表中。这个Leads表由数百万条记录组成,每秒钟增长8条记录。表结构如下:Mysql:索引计数查询与维护汇总表

LeadId | ProductId | UserId | RequestDate(DateTime) 

表模式:现在

`id` int(11) NOT NULL AUTO_INCREMENT, 
`ProductId` int(11) DEFAULT NULL, 
`UserID` int(11) NOT NULL, 
`RequestDateTime` datetime(3) NOT NULL, 
PRIMARY KEY (`id`), 
KEY `ix_leads_requestdatetime` (`RequestDateTime`) USING BTREE, 
KEY `ix_leads_productid` (`ProductId`) USING BTREE, 
KEY `ix_leads_userid` (`UserID`) USING BTREE 

的要求是,让一个用户提供最大10根引线一天。我有如下的方法来实现这一点:

  1. 选择查询到Leads表计数的记录数为一天,插入前检查是否< 20。

  2. 维护DailyLeadCount表,其中包含特定日期的每个userId的导联计数。表结构:

    UserId | Date | Count 
    

    表模式:

    `RequestDate` date NOT NULL, 
    `UserId` int(11) NOT NULL, 
    `LeadCount` smallint(6) NOT NULL, 
    PRIMARY KEY (`RequestDate`,`UserId`) 
    

    我将在这个表来检查计数Leads表中插入之前并相应地更新插入后此计数。另外,由于在此表中只有一天数据有用,我将创建一份工作,以便每天对其进行归档。

哪种方法更好?正在运行Leads表上的select查询得到的计数比插入/更新更重,并在DailyLeadCount表上选择查询?

是否值得每天维护和存档表格?

有没有其他办法可以解决这个问题?

+0

第三种选择是构造插入语句,以便将检查包含在具有子查询的where子句中。你能显示表格模式,包括索引吗? –

+0

@SloanThrasher添加了表格模式。并且,如果在存储过程中,在where子句中添加子查询在性能方面等于approach-1。不是吗? – ctor

+0

不完全相同。 #1,你有两个单独的查询,选择和插入。找出最好的方法是编写两个查询并使用Explain来查看服务器如何感知要完成的工作。 –

变化

KEY `ix_leads_userid` (`UserID`) USING BTREE 

INDEX(UserID, RequestDateTime) 

然后在用户吐时

(SELECT COUNT(*) FROM Leads WHERE UserID = 1234 
     AND RequestDateTime > NOW() - INTERVAL 24 HOUR 
) >= 10 

查询将足够快,实时地做。

计数是在这段时间之间的昨天和现在 - 这可能不完全是你想要的。相反,如果你希望时钟在午夜今天上午开始:

 AND RequestDateTime > CURDATE() 

如果“自昨天午夜”:

 AND RequestDateTime > CURDATE() - INTERVAL 1 DAY 

如果你想使用时区的午夜,它会混乱。

潜在问题:如果他能以某种方式批量处理他的潜在客户,他可以在同一毫秒内插入多个潜在客户。 (我注意到DATETIME(3)。)

如果您需要检查“昨天”,对于“最后的86400000毫秒”不太满意,您对摘要表的想法效果最佳。

+0

当总结表更好时,我有点困惑。我需要检查“当前日期”的计数(即时钟在今天午夜重置),而不是最近24小时。如果您表示总结不适用于最后的“x”单位时间,但会更好地适用于“上次日期”。在我的情况下(当前日期)它不会有用吗? – ctor

+0

如果你只看“今天”,那么你不需要总结前几天。总结“今天”最好在今晚午夜之后完成。 –