Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/unit-testing/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php MySQL快速从300行中随机选择20行_Php_Mysql_Sql_Select_Random - Fatal编程技术网

Php MySQL快速从300行中随机选择20行

Php MySQL快速从300行中随机选择20行,php,mysql,sql,select,random,Php,Mysql,Sql,Select,Random,我的数据库目前有300行,未来几年可能会增加到5000行左右。我想知道我怎样才能最好地随机选择20行 我在这里发现(这里再次提到)以下代码生成随机选择的速度非常快: SELECT name FROM random AS r1 JOIN (SELECT (RAND() * (SELECT MAX(id) FROM random)) AS id) AS r2 WHERE r1

我的数据库目前有300行,未来几年可能会增加到5000行左右。我想知道我怎样才能最好地随机选择20行

我在这里发现(这里再次提到)以下代码生成随机选择的速度非常快:

SELECT name
  FROM random AS r1 JOIN
       (SELECT (RAND() *
                     (SELECT MAX(id)
                        FROM random)) AS id)
        AS r2
 WHERE r1.id >= r2.id
 ORDER BY r1.id ASC
 LIMIT 1
因此,在php中,我尝试了以下方法来获得20行:

$anfrage    =   "SELECT name
  FROM random AS r1 JOIN
       (SELECT (RAND() *
                     (SELECT MAX(id)
                        FROM random)) AS id)
        AS r2
 WHERE r1.id >= r2.id
 ORDER BY r1.id ASC
 LIMIT 20";

 $ergebnis=$db->query($anfrage)
        or die($db->error);
 while($zeile=mysqli_fetch_assoc($ergebnis))print_r($zeile);
但是当我运行脚本时,大多数时候我不会得到20行。实际上,从300行中选择20行的概率约为48.8%

我可以更改上面的代码以快速获得20行吗

如果你阅读了你在问题中提到的答案,你会发现有3种解决方案:

  • 执行查询几次
  • 编写一个执行查询的存储过程,并将结果存储在临时表中
  • 结成联盟
所有这些都在本文中进行了解释。

获得20个随机名称的“慢”方法如下:

SELECT name
FROM random 
ORDER BY rand()
LIMIT 20;
在300行上,这可能与您正在使用的方法具有类似的性能。你试过了吗?我不确定大约5000行,但在那里也值得一试

您的方法基本上是这样的(查询有点简化):

您假设使用不同的值为每个迭代计算
r2
。这一假设可能不正确

另一种方法是:

SELECT name
FROM random r1 CROSS JOIN
     (SELECT count(*) as cnt FROM random) const
WHERE rand() <= 20.0 / cnt;

您可以创建一个偶尔更新的无序表:

INSERT INTO random_ids 
SELECT id 
FROM table_name
ORDER BY RAND();
记录在应用程序中插入的随机值的数量;然后使用以下命令:

SELECT * FROM table_name
INNER JOIN (SELECT id 
    FROM random_ids
    LIMIT ?,20
) r1 ON r1.id = table_name.id;

如果应用程序确定限制在
[0,)

的范围内,那么问题是r2.id可能是299,因此只有两行“r1.id>=r2.id”是true@niccomatik我想我必须将Limit设置为“1”,并在循环中执行整个查询。然后在每次查询之后,我必须检查获得的行是否是新的行-这就是它的工作原理吗?即使是50000行,简单的随机选择也会很快。5000行不算什么。MySQL可能甚至不会在查询的表上使用索引,这些表的大小更容易定义必须扫描一张表,所以我不知道您为什么担心速度。有趣的问题是,您是否尝试应用
RAND()*(选择MAX(id)-20…
?:)
INSERT INTO random_ids 
SELECT id 
FROM table_name
ORDER BY RAND();
SELECT * FROM table_name
INNER JOIN (SELECT id 
    FROM random_ids
    LIMIT ?,20
) r1 ON r1.id = table_name.id;