首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >使用超过10万条记录优化MySQL查询

使用超过10万条记录优化MySQL查询
EN

Stack Overflow用户
提问于 2021-07-28 08:28:19
回答 2查看 294关注 0票数 0

我希望你能帮我优化这个查询。

代码语言:javascript
运行
复制
SELECT  carrier,
        SUM(views) AS views,
        SUM(views-1) AS repeated,
        SUM(views >= 1) AS unique_views,
        COUNT(1) AS total
    FROM  stats s1
    WHERE  id_link = 39
      AND  EXISTS (
        SELECT  *
            FROM  stats s2
            where  id_link = 39
              AND  s2.carrier = s1.carrier
            LIMIT  1, 1 )
    GROUP BY  carrier
    HAVING  COUNT(1) >= 1
    LIMIT  1,1
 UNION 
 SELECT  'TOTAL' AS carrier,
        SUM(views) AS views,
        SUM(views-1) AS repeated,
        SUM(views >= 1) AS unique_views,
        COUNT(1) AS total
    FROM  stats s4
    WHERE  id_link = 39
      AND  EXISTS (
        SELECT  *
            FROM  stats s3
            where  s3.carrier = s4.carrier
            LIMIT  1, 1 )

数据库:

代码语言:javascript
运行
复制
CREATE TABLE `stats` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`id_link` int(11) NOT NULL,
`country` varchar(100) NOT NULL,
`ip` varchar(100) NOT NULL,
`views` varchar(1000) NOT NULL,
`asn` varchar(1000) NOT NULL,
`carrier` varchar(1000) NOT NULL,
`type` varchar(1000) NOT NULL,
`device` varchar(1000) NOT NULL,
`browser` varchar(1000) NOT NULL,
`fecha` datetime NOT NULL,
`referrer` varchar(2000) NOT NULL,
PRIMARY KEY (`id`),
KEY `id_link` (`id_link`),
CONSTRAINT `stats_ibfk_1` FOREIGN KEY (`id_link`) REFERENCES `campaigns` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB AUTO_INCREMENT=614606 DEFAULT CHARSET=utf8

我正在创建一个网络流量跟踪器。我有一个名为"stats“的表,在这里我保存;视图、ASN、IP、浏览器、设备和其他东西,其中包括”载体“,即互联网服务提供商。

我想要的是看看每个运营商有多少次访问,账户重复不止一次,有多少次有独特的访问。

我已经完成了我想做的代码,但是只有当记录很少时,它才能工作,现在服务器崩溃的记录超过了100 k,它不加载查询,甚至不得不重新启动apache。

在这里,我只留下一个说明性的图像

有办法加快查询速度吗?

提前感谢您的评论和帮助。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2021-07-28 17:10:47

** views被用作数字。如果是这样的话,不要使用VARCHAR。建议INT UNSIGNED (最高值为40亿)。

**使用合理的限制,而不是varchar(1000)

**越小越快。所以..。使重复的列规范化。carrier大约有9个不同的值?一个SMALLINT UNSIGNED只需要两个字节,并且有足够的空间来处理所有的载波。大多数varchar(1000)也是如此。

**建议使用标准的2-字母"country_code“(CHAR(2))代替country(100) -- IN,US,UK,FR,.

**专门用于加速查询、更改

代码语言:javascript
运行
复制
KEY `id_link` (`id_link`),

代码语言:javascript
运行
复制
KEY `id_link` (`id_link`, carrier),

**考虑在WITH ROLLUP中使用GROUP BY,这样就不需要UNION和第二个SELECT了。

**考虑建立和维持一个每日小计的“简表”。查询此表的速度将比当前的原始(“事实”)表快得多。更多信息:http://mysql.rjweb.org/doc.php/summarytables。(这说明了Shubham在评论中提到的内容。)

票数 0
EN

Stack Overflow用户

发布于 2021-07-28 08:41:33

您可以使用Mysql OffSet和限制来实现它。

您可以尝试使用ajax,在第一次加载1500记录,在滚动或单击下一个加载下1500记录,使用数据,它有内部分页+附加下一个按钮获得更多的结果,例如在第1页偏移= 0,极限= 1500页偏移= 1500,极限1500。诸若此类

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/68556931

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档