现在有个需求,就是随机获取数据库表中的一条数据,如果用java的话,很简单。都查出来,然后搞一个随机数取List的一条数据,但是,如果数据量过大的话,都查出来会非常的占内存,所以显然不合适。那么,用sql的话,应该如何实现呢?
方式一:
select * from tb_ip_poll order by rand() limit 1;
这个实现很简单,如果数据量小的话,强烈推荐这样的写法。就是利用rand函数来排序,然后取第一个数据即可。数据量大的话可能会效率的问题。
方式二:
SELECT * FROM `table`WHERE id >= (SELECT FLOOR(RAND() * (SELECT MAX(id) FROM `table`)))ORDER BY id LIMIT 1;
评价: 这个方法还是有缺陷的,如果id不是从0开始的话,比如从10000开始自增,那么SELECT floor(RAND() * (SELECT MAX(id) FROM table))
得到的将是会有很大概率得到小于10000的值,经过where限定的查询结果将会是所有的查询结果的几率变大,最后limit 1
获取的是第一行数据的几率变高。
方式三:
SELECT * FROM TABLEWHEREid >= ( SELECT FLOOR(RAND()* ((SELECT MAX( id ) FROM TABLE ) -(SELECT MIN( id ) FROM TABLE ))+ ( SELECT MIN( id ) FROM TABLE )))ORDER BY id LIMIT 1;
评价: 解决了方法2的问题,但仍然有缺陷,如果有一个数据id为1,其余都是10000以上,那么效果与方法2几乎一致,因此部分数据的id有较大跨度时也会导致结果不平均
方式四:
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 t2WHERE t1.id >= t2.idORDER BY t1.id LIMIT 1;
评价:解决了方法二中MAX(id)的问题,RAND() * ((SELECT MAX(id) FROM table) - (SELECT MIN(id) FROM table)) + (SELECT MIN(id) FROM table)
可以获取MAX(id)和MIN(id)中的随机数。
文章转载自干货食堂,如果涉嫌侵权,请发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。




