[求助] desc limit N 场景性能比asc limit N 相差千倍

【详述】table1表中createTime作为第一个sort key,类型datetime(timestamp)
当我执行以下语句,order by 是asc时,大概0.1s。
SELECT * FROM table1 WHERE createTime >= ‘2023-07-01 00:00:00.0’ AND createTime <= ‘2023-07-03 23:59:59.0’ ORDER BY createTime ASC LIMIT 10;
但是,同样的查询,改成desc,却花了大概12s。
SELECT * FROM table1 WHERE createTime >= ‘2023-07-01 00:00:00.0’ AND createTime <= ‘2023-07-03 23:59:59.0’ ORDER BY createTime DESC LIMIT 10;
我查看了profile文件,发现两者读取的数据量相差1000倍左右。
请问这种情况应该如何优化?
我理解,在sort key和前缀索引的前提下,asc limit 10和desc limit 10,读取的数据量应该大概差不多,性能也不应该相差太多。而desc top N的场景在工作中非常常见,如倒序取topN。


【业务影响】desc top N 场景性能较差
【StarRocks版本】StarRocks version 3.0.3
【集群规模】FE 3 + BE 3
【联系方式】jie zhang(ijavatar@126.com)

模型是 DUPLICATE KEY 模型

3.0.3版本对吧 麻烦发下这个两个查询的profile 我来跟进下

desc.pref (29.3 KB) asc.pref (28.9 KB)

文件已添附,麻烦您。

麻烦您跟进,谢谢

目前我们没有在scan上专门针对topn优化,因为topn asc的runtime filter可以大批量过滤scan数据会比较快,这个对desc的优化效果比较小,我提个改进 后续我们会优化下 感谢

多谢!还请评估下,能否帮我们提高优先级。
这个场景业务中其实挺多的。因为OLAP的报表、大屏、首页都需要这种最新N条、还有分页的场景。

1赞

好的理解 我已提交对应的改进信息给产品同学了

帮忙验证个SQL
select * from table where createTime in (select createTime from table order by createTime desc limit 10);
看看要能跑多久

您的写法很有道理。我们之前测试过select createTime from table order by createTime desc limit 10这个,返回时间大概在0.35s左右。所以不明白为何之后的回表操作会花这么多时间。

这张压测表已被清除,我找了另外一张数据量少一些的表测试了一下。结果如下:
select * from user_log WHERE createTime >= ‘2010-07-01 00:00:00.0’ AND createTime <= ‘2023-07-16 23:59:59.0’ order by createTime asc limit 10 offset 10000;
10 rows in set (0.64 sec)

select * from user_log WHERE createTime >= ‘2010-07-01 00:00:00.0’ AND createTime <= ‘2023-07-16 23:59:59.0’ order by createTime desc limit 10 offset 1000;
10 rows in set (4.14 sec)

select * from user_log where createTime in (select createTime from user_log order by createTime asc limit 10 offset 1000000) order by createTime asc limit 10;
10 rows in set (0.42 sec)

select * from user_log where createTime in (select createTime from user_log order by createTime desc limit 10 offset 1000000) order by createTime desc limit 10;
10 rows in set (0.82 sec)
desc目前的实现逻辑应该是不太好的,但您提示的这种利用asc的这种写法可以利用索引和前缀索引。感谢。

这个方法虽然能临时解决问题,但还请产品方从底层优化desc的做法。因为这个方法意味着所有这些逻辑都需要去这样改写。语义上还是不方便的。

这个profile发一下我看看,另外设置一下 set enable_shared_scan=true; 看看desc能不能快点

asc和desc的profile文件已添附在上面,请查看。

麻烦您。

最近实现了一个demo,测试来看有不错的效果 加个微信给你一个包看看效果? @ijavatar

CHN10151

加了您说的这个配置,但是desc还是很慢,asc基本零点几秒就好了,desc都快接近十秒了 limit 1000,100,数据量我们也才两亿不到

目前对于desc有个临时版本,可以加我微信替换个包试一下

这个branch优化了 https://github.com/StarRocks/starrocks/commits/desc_topn_optimize_0911

您好,正式版本大概什么时候有

这个feature还在preview阶段,需要找用户试用