大型SELECT查询似乎返回相同但较小的SELECT查询的不同顺序?

问题描述 投票:1回答:3

我正在执行SQLite查询以获取一堆图像ID的所有图像路径。需要维护ID的顺序。如果我查询5个ID,则以正确的顺序返回5个路径。但是,如果我保持查询完全相同但查询72,000个ID,我收到的订单是不同的?

为什么会这样?我复制并粘贴了2个查询和2个结果(显然减去了完整的72,000个ID和结果)。

这对任何人都有意义吗?

查询(有5个ID)

SELECT Path FROM Images WHERE MicrosoftId IN ('78003','78010','78080','78149','78196')

结果(这是正确的!)

"~/ImagesPath/36/20160818_082235_000.jpg"
"~/ImagesPath/36/20160818_082904_000.jpg"
"~/ImagesPath/36/20160818_092336_000.jpg"
"~/ImagesPath/36/20160818_101818_000.jpg"
"~/ImagesPath/36/20160818_105621_000.jpg"

查询(具有72,000个ID)

SELECT Path FROM Images WHERE MicrosoftId IN (('78003','78010','78080','78149','78196','78229','78231','78236','78237','78238','78248','78250'...etc 72,000 more)

结果(这是不正确的!为什么订单改变?)

"~/ImagesPath/36/20160818_050623_000.jpg"
"~/ImagesPath/36/20160818_050710_000.jpg"
"~/ImagesPath/36/20160818_050844_000.jpg"
"~/ImagesPath/36/20160818_050449_000.jpg"
"~/ImagesPath/36/20160818_050757_000.jpg"
etc... to 72,000

编辑:你会如何加入这两个查询?

SELECT MicrosoftId FROM TagsMSCV WHERE name IN ('" + some vars + "') GROUP BY MicrosoftId ORDER BY COUNT(MicrosoftId) DESC

SELECT Path FROM Images WHERE MicrosoftId IN ('" + results from above query + "')
sql sqlite
3个回答
1
投票
SELECT Path FROM Images i
JOIN TagsMSCV t ON i.MicrosoftId = t.MicrosoftId
WHERE t.name IN ('" + some vars + "') GROUP BY t.MicrosoftId ORDER BY
COUNT(t.MicrosoftId) DESC

这个连接应该可以解决问题


1
投票

如果没有明确指定order by子句,则无法保证返回行的顺序。数据库可以以最有效的顺序自由返回它们。即使你确实按照你想要的顺序得到结果,你也不能指望它 - 任何数量的情况(例如,重建索引,或者只是碰巧在某个缓存上的一行)可能会改变顺序下次你运行quetry。

TL; DR,如果你关心行的顺序,你应该添加一个order by子句:

SELECT   Path 
FROM     Images
WHERE    MicrosoftId IN ('78003','78010','78080','78149','78196', /* etc ...*/)
ORDER BY MicrosoftId

1
投票

一种解决方案是将您的查询组织到JOIN

select * from
    (
        select 78003 as mid
        union select 78010
        union select 78080
        union select 78149
        union select 78196
        # and so on...
    ) mids
    inner join Images on (Images.MicrosoftId = mids.mid);

这样,查询应该使用构造的mids表的顺序。

如果您想对订购更加确定,可以在构建的表的订购列上添加:

select * from
    (
        select 78003 as mid, 1 as midOrder
        union select 78010, 2
        union select 78080, 3
        union select 78149, 4
        union select 78196, 5
        # and so on...
    ) mids
    inner join Images on (Images.MicrosoftId = mids.mid)
    order by midOrder
© www.soinside.com 2019 - 2024. All rights reserved.