mysql 随机查询 效率比较

select
    primary_count as primaryCount,
    primary_score as primaryScore,
    junior_count as juniorCount,
    junior_score as juniorScore,
    senior_count as seniorCount,
    senoir_score as senoirScore,
    total_score as totalScore,
    pass_score as passScore
from pd_paper p
where p.is_valid = ‘1‘
order by RAND() limit 1

分析:
ORDER BY从句里面不能使用RAND()函数,因为这样会导致数据列被多次扫描。
测试发现这样效率非常低。一个15万余条的库,查询5条数据,要8秒以上。

You cannot use a column with RAND() values in an ORDER BY clause, because ORDER BY
would evaluate the column multiple times.

更高效的做法:查询max(id) * rand()来随机获取数据。

SELECT *
FROM `table` AS t1
JOIN (
    SELECT ROUND(RAND()
    * (SELECT MAX(id) FROM `table`)) AS id
) AS t2
WHERE t1.id >= t2.id
ORDER BY t1.id ASC LIMIT 5;

但是这样会产生连续的5条记录。解决办法只能是每次查询一条,查询5次。
即便如此也值得,因为15万条的表,查询只需要0.01秒不到。
采用join 语法  可以实现真正的随机。

SELECT *
FROM `table`
WHERE id >= (SELECT FLOOR( MAX(id) * RAND()) FROM `table` )
ORDER BY id LIMIT 1;

把语句完善一下,加上MIN(id)的判断。
如果没有加上MIN(id)的判断,结果有一半的时间总是查询到表中的前面几行。
完整的语句:

①  where 子句

SELECT * FROM `table`
WHERE id >= (SELECT floor( RAND() * ((SELECT MAX(id) FROM `table`)-
 (SELECT MIN(id) FROM `table`)) + (SELECT MIN(id) FROM `table`)))
ORDER BY id LIMIT 1;

② join

SELECT *
FROM `table` AS t1
JOIN (
    SELECT ROUND(RAND()
    * ((SELECT MAX(id) FROM `table`)-(SELECT MIN(id) FROM `table`))
    +(SELECT MIN(id) FROM `table`)) AS id) AS t2
WHERE t1.id >= t2.id
ORDER BY t1.id LIMIT 1;

#随机查询一套考卷定义
SELECT
    p.primary_count as primaryCount,
    p.primary_score as primaryScore,
    p.junior_count as juniorCount,
    p.junior_score as juniorScore,
    p.senior_count as seniorCount,
    p.senoir_score as senoirScore,
    p.total_score   as totalScore,
    p.pass_score as passScore   

FROM
    pd_paper AS p
JOIN
(
    SELECT ROUND(
        RAND()
        *((SELECT MAX(id) FROM pd_paper)-(SELECT MIN(id) FROM pd_paper))
        +(SELECT MIN(id) FROM pd_paper)
    ) AS id
)
    AS p2
WHERE p.id >= p2.id
ORDER BY p.id LIMIT 1;

最后在程序对这两个语句进行分别查询10次,
前者花费时间 0.147433 秒
后者花费时间 0.015130 秒
看来采用JOIN的语法比直接在WHERE中使用函数效率还要高很多。

附加一个复杂sql:按题目类型(三种)随机查询全部考题信息

SELECT * from (
    select
        p.id as id,
        p.title as title,
        p.question as question,
        p.answer as answer,
        p.crt_time as crtTime
    from
        pd_problem p
    join
        (SELECT ROUND(RAND()
            * ((SELECT MAX(pp.id) FROM pd_problem pp)-(SELECT MIN(pp.id) FROM pd_problem pp))
            +(SELECT MIN(pp.id) FROM pd_problem pp)) AS pid) AS p2
    where p.id >= p2.pid
    and p.is_valid = ‘1‘
    and p.paper_type = ‘1‘
    and p.paper_class = ‘0‘
    order by p.id limit 5
 ) as t1
 union all
 SELECT * from (
    select
        p.id as id,
        p.title as title,
        p.question as question,
        p.answer as answer,
        p.crt_time as crtTime
    from
        pd_problem p
    join
        (SELECT ROUND(RAND()
            * ((SELECT MAX(pp.id) FROM pd_problem pp)-(SELECT MIN(pp.id) FROM pd_problem pp))
            +(SELECT MIN(pp.id) FROM pd_problem pp)) AS pid) AS p2
    where p.id >= p2.pid
    and p.is_valid = ‘1‘
    and p.paper_type = ‘1‘
    and p.paper_class = ‘1‘
    order by p.id limit 5
 ) as t2
 union all
 SELECT * from (
    select
        p.id as id,
        p.title as title,
        p.question as question,
        p.answer as answer,
        p.crt_time as crtTime
    from
        pd_problem p
    join
        (SELECT ROUND(RAND()
            * ((SELECT MAX(pp.id) FROM pd_problem pp)-(SELECT MIN(pp.id) FROM pd_problem pp))
            +(SELECT MIN(pp.id) FROM pd_problem pp)) AS pid) AS p2
    where p.id >= p2.pid
    and p.is_valid = ‘1‘
    and p.paper_type = ‘1‘
    and p.paper_class = ‘2‘
    order by p.id limit 5
 ) as t3

mysql 随机查询 效率比较

时间: 2024-08-08 22:01:01

mysql 随机查询 效率比较的相关文章

mysql随机查询记录的高效率方法

mysql使用rand随机查询记录的高效率方法 一直以为mysql随机查询几条数据,就用 SELECT * FROM `table` ORDER BY RAND() LIMIT 5 就可以了. 但是真正测试一下才发现这样效率非常低.一个15万余条的库,查询5条数据,居然要8秒以上 查看官方手册,也说rand()放在ORDER BY 子句中会被执行多次,自然效率及很低. You cannot use a column with RAND() values in an ORDER BY clause

如何实现MySQL随机查询数据与MySQL随机更新数据?

以下的文章主要介绍的是MySQL随机选取数据,对实现MySQ随机查询数据与MySQ随机更新数据的实际操作步骤的描述,以及对其实际操作中所要用到的语句的描述,以下就是对其具体操作步骤的描述. MySQL随机查询数据 以前在群里讨论过这个问题,比较的有意思.mysql的语法真好玩.他们原来都想用PHP的实现随机,但取出多条好像要进行两次以上查询.翻了手册,找到了下面这个语句,可以完成任务了. SELECT * FROM table_name ORDER BY rand() LIMIT 5; MySQ

提高MySQL数据库查询效率的几个技巧(转载)

[size=5][color=Red]提高MySQL数据库查询效率的几个技巧(转)[/color][/size]      MySQL由于它本身的小巧和操作的高效, 在数据库应用中越来越多的被采用.我在开发一个P2P应用的时候曾经使用MySQL来保存P2P节点,由于P2P的应用中,结点数动辄上万个,而且节点变化频繁,因此一定要保持查询和插入的高效.以下是我在使用过程中做的提高效率的三个有效的尝试. l 使用statement进行绑定查询 使用statement可以提前构建查询语法树,在查询时不再

mysql随机查询符合条件的几条记录

随机查询,方法可以有很多种.比如,查询出所有记录,然后随机从列表中取n条记录.使用程序便可实现.可是程序实现必须查询出所有符合条件的记录(至少是所有符合条件的记录id),然后再随机取出n个id,查询数据库.但是效率毕竟没有数据库中直接查询得快.下面介绍mysql中怎样随机查询n条记录. 1.最简单的办法order by rand(),示例 select * from question q where q.`level`=1 order by rand() limit 1; 此写法,可以将查询出的

如何提高Mysql的查询效率???

1.对查询进行优化,应尽量避免全表扫描,首先应考虑在 where 及 order by 涉及的列上建立索引. 2.应尽量避免在 where 子句中对字段进行 null 值判断,否则将导致引擎放弃使用索引而进行全表扫描,如: select id from t where num is null 可以在num上设置默认值0,确保表中num列没有null值,然后这样查询: select id from t where num=0 3.应尽量避免在 where 子句中使用!=或<>操作符,否则将引擎放

提高mysql数据库查询效率

在一个千万级的数据库查寻中,如何提高查询效率? 1)数据库设计方面: a. 对查询进行优化,应尽量避免全表扫描,首先应考虑在 where 及 order by 涉及的列上建立索引. b. 应尽量避免在 where 子句中对字段进行 null 值判断,否则将导致引擎放弃使用索引而进行全表扫描,如: select id from t where num is null 可以在num上设置默认值0,确保表中num列没有null值,然后这样查询: select id from t where num=0

MySQL联合查询语法内联、左联、右联、全联

MySQL联合查询效率较高,以下例子来说明联合查询(内联.左联.右联.全联)的好处: T1表结构(用户id,用户名,密码)   userid   username  password 1   jack jackpwd    2   owen   owenpwd T2表结构(用户id,用户积分,用户等级)   userid(int)   jifen   dengji     1    20   3       3    50    6 第一:内联( inner join )如果想把用户信息.积分.

MYSQL随机抽取查询 MySQL Order By Rand()效率问题

MYSQL随机抽取查询:MySQL Order By Rand()效率问题一直是开发人员的常见问题,俺们不是DBA,没有那么牛B,所只能慢慢研究咯,最近由于项目问题,需要大概研究了一下MYSQL的随机抽取实现方法 要从tablename表中随机提取一条记录,大家一般的写法就是:SELECT * FROM tablename ORDER BY RAND() LIMIT 1. 但是,后来我查了一下MYSQL的官方手册,里面针对RAND()的提示大概意思就是,在ORDER BY从句里面不能使用RAND

MySQL使用rand 随机查询记录效率测试

以下的文章主要介绍的是MySQL使用rand 随机查询记录效率测试,我们大家一直都以为MySQL数据库随机查询的几条数据,就用以下的东东,其实其实际效率是十分低的,以下就是文章的主要内容. SELECT * FROM `table` ORDER BY RAND() LIMIT 5 就可以了.但是真正测试一下才发现这样效率非常低.一个15万余条的库,查询5条数据,居然要8秒以上 查看官方手册,也说rand()放在ORDER BY 子句中会被执行多次,自然效率及很低. You cannot use