【问题标题】:Print a random row from a mysql query从 mysql 查询中打印随机行
【发布时间】:2014-12-30 06:49:41
【问题描述】:

我一直在寻找一种创建协作翻译小部件的方法。所以我有一个 mysql 数据库和表(称为翻译),以及一个允许用户一次翻译一页的小脚本。

但我不太相信我的剧本。我认为它不够有效。首先,mysql 获取所有“en”列为空的行,然后在屏幕上显示其中的一个。有没有其他方法可以做到这一点?这是代码:

//Retrieve all the data from the "translations" table
$result = mysql_query("SELECT * FROM translations WHERE en IS NULL OR en=''") or die(mysql_error());

$Randnum=rand(0,mysql_num_rows($result)-1); //Gets a random number between 0 and the maximum number of rows
$i=0;   //Start to 0
while($Col = mysql_fetch_array($result))  //While there are rows to evaluate
    {
    if ($i==$Randnum)
        {
        echo "\"".$Col['es']."\"<br><br>Translate it to English: <br>";
        }
    $i++;
    }

我一直在寻找类似 "echo $Col[$Randnum]['es']" 或 "echo $Col.$Randnum['es']" 的东西,而不是使用整个 while 循环来打印单个随机行。我该如何实现?如果只是优化问题。如果您可以提供一个脚本或想法来分配给 $Col 仅一行带有随机数和空的“en”col,那就更好了! (我认为这最后一点是不可能的)。 'en' 行是文本,所以我不知道如何实现 other methods,因为他们使用数字和 ORDER BY。

【问题讨论】:

    标签: php mysql optimization


    【解决方案1】:

    您可以在查询中使用ORDER BY RAND() LIMIT 1 从数据库中获取单个随机行。

    【讨论】:

    • 即使是文本也能工作吗?即使它有效,它不会选择具有第一个 ASCII 的文本作为 rand() 所说的吗? (例如,如果许多行以 'H' 开头,那么每次 rand() 为 72 时,它不会只选择第一个吗?)
    • @FrankPresenciaFandos:这与您表中的数据完全无关。它在内部为每一行生成一个随机数,然后按该数排序。
    • 然后它不像“ORDER BY en”那样工作,它实际上会按这些列中的文本对结果进行排序。我不知道,谢谢!
    【解决方案2】:

    在查询端制作

    SELECT * FROM translations WHERE en IS NULL OR en='' ORDER BY rand() LIMIT 0,1
    

    【讨论】:

      【解决方案3】:

      有几种方法可以做到这一点。

      @ThiefMaster 的回答会起作用——但“order by rand()”在大型表上存在相当大的性能问题。因此,我将使用您希望能够增长到的大小的样本数据填充您的表,并测试性能。如果这不是问题,请保持原样 - 过早优化是万恶之源!

      有一些alternatives;他们依赖于运行两个独立的查询;但是,假设您有索引,那应该不是问题。

      为您的场景重新设计,变为:

      mysql_query('SELECT @count := COUNT(*) FROM translations WHERE en IS NULL OR en=''');
      mysql_query('SET @offset = CONVERT(FLOOR(RAND() * @count), SIGNED)');
      mysql_query('PREPARE mystatement FROM "SELECT * FROM translations WHERE en IS NULL OR en='' LIMIT ?, 1"');
      $res = mysql_query('EXECUTE mystatement USING @offset');
      $row = mysql_fetch_assoc($res);
      print_r($row);
      

      【讨论】:

      • 我预计此表将来不会超过 2000/3000 行,但感谢您扩展信息。我也喜欢“过早的优化是万恶之源”这句话。
      • 这不是我的 - 有人指出,将“过早”放在几乎任何东西前面都会让人觉得很糟糕......
      • 对不起,我的意思是,感谢您的引述,让我在互联网上阅读了许多不同的有趣内容(;
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-02
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多