社区所有版块导航
Python
python开源   Django   Python   DjangoApp   pycharm  
DATA
docker   Elasticsearch  
aigc
aigc   chatgpt  
WEB开发
linux   MongoDB   Redis   DATABASE   NGINX   其他Web框架   web工具   zookeeper   tornado   NoSql   Bootstrap   js   peewee   Git   bottle   IE   MQ   Jquery  
机器学习
机器学习算法  
Python88.com
反馈   公告   社区推广  
产品
短视频  
印度
印度  
Py学习  »  DATABASE

为什么我的MySQL程序应该选择一个随机行,而只选择三个特定值中的一个?

just_another_question • 3 年前 • 1284 次点击  

我有一个名为 quote_of_the_day 它应该从列表中选择不同的行 quotes 表中的日期作为种子值。当我将代码作为查询进行测试时,一切似乎都运行良好,但当我在php代码中调用函数时(查询是 CALL quote_of_the_day() )它只会从三个不同的引号中选择一个,尽管表中有23个引号。

创建systax for 引用今天的话 是:

DELIMITER ;;
CREATE DEFINER=`root`@`%` PROCEDURE `quote_of_the_day`()
BEGIN
        # save the number of rows into a variable
        SET @num_rows = (SELECT COUNT(*) FROM `quotes`);

        # calculate a random number no greater than the number of rows in the table
        SET @rand_num = (SELECT FLOOR(RAND(CURDATE())*(@num_rows+1)));

        # select random quote from the list of quotes (seed value is the current day)
        SELECT quote FROM quotes WHERE id = @rand_num;
        
        # increment the quoted column to keep track of which quotes are selected
        UPDATE quotes SET quoted = quoted + 1 WHERE id = @rand_num AND last_used <> CURDATE();
        UPDATE quotes SET last_used = CURDATE() WHERE id = @rand_num;
    END;;
DELIMITER ;

我哪里做错了?

Python社区是高质量的Python/Django开发社区
本文地址:http://www.python88.com/topic/127950
 
1284 次点击  
文章 [ 2 ]  |  最新文章 3 年前
Bohemian
Reply   •   1 楼
Bohemian    3 年前

您的seed在日期的年份保持不变,因为当MySQL将字符串转换为日期时,它使用它在字符串中找到的第一个数字字符串,该字符串当前为 2021 .

使用 TO_DAYS() 种子 RAND() 自去年以来的天数 0 :

RAND(TO_DAYS(CURDATE()))

每一天都将永远传递一个不同的、但在当前日期不变的值 rand()

Bill Karwin
Reply   •   2 楼
Bill Karwin    3 年前

上面的评论是在用答案取笑你。

请阅读MySQL上的手册 RAND() function :

...对于相等的参数值,RAND(N)每次返回相同的值,从而生成一个可重复的列值序列。在下面的示例中,RAND(3)生成的值序列在两个位置都是相同的。

由于CURDATE()在同一天内每次调用时都返回一个常量值,因此将其传递给RAND()会使RAND()在每次调用时都返回相同的值。

演示:

mysql> select rand(curdate());
+------------------+
| rand(curdate())  |
+------------------+
| 0.49455075570806 |
+------------------+
1 row in set (0.00 sec)

mysql> select rand(curdate());
+------------------+
| rand(curdate())  |
+------------------+
| 0.49455075570806 |
+------------------+
1 row in set (0.00 sec)

mysql> select rand(curdate());
+------------------+
| rand(curdate())  |
+------------------+
| 0.49455075570806 |
+------------------+
1 row in set (0.00 sec)

mysql> select rand(curdate());
+------------------+
| rand(curdate())  |
+------------------+
| 0.49455075570806 |
+------------------+
1 row in set (0.00 sec)

这将一直持续到我的时钟显示这是新的一天。

实际上不需要将值传递给seed RAND()。当MySQL服务器启动时,它会得到一个种子,并继续生成随机值。

当需要一系列新的随机值时,不要使用seed参数,当需要 可复制的随机值序列 ,例如,如果您正在运行自动测试。


请回复您的评论:

RAND()的参数是一个整数,但像“2021-11-07”这样的日期将作为字符串返回。在数值上下文中,“2021-11-07”的整数值为2021。任何非数字字符在作为参数传递给RAND()之前都会被去除。

mysql> select rand('2021-11-04');
+--------------------+
| rand('2021-11-04') |
+--------------------+
| 0.7752841103591808 |
+--------------------+
1 row in set, 1 warning (0.00 sec)

mysql> select rand('2021-11-05');
+--------------------+
| rand('2021-11-05') |
+--------------------+
| 0.7752841103591808 |
+--------------------+
1 row in set, 1 warning (0.00 sec)

mysql> select rand('2021-11-06');
+--------------------+
| rand('2021-11-06') |
+--------------------+
| 0.7752841103591808 |
+--------------------+
1 row in set, 1 warning (0.00 sec)

mysql> select rand('2021-11-07');
+--------------------+
| rand('2021-11-07') |
+--------------------+
| 0.7752841103591808 |
+--------------------+
1 row in set, 1 warning (0.00 sec)

你可以看到它是这样做的:

mysql> show warnings;
+---------+------+-------------------------------------------------+
| Level   | Code | Message                                         |
+---------+------+-------------------------------------------------+
| Warning | 1292 | Truncated incorrect INTEGER value: '2021-11-07' |
+---------+------+-------------------------------------------------+

所有这些日期都在播种随机数,好像你只通过了“2021”或2021作为参数:

mysql> select rand('2021');
+--------------------+
| rand('2021')       |
+--------------------+
| 0.7752841103591808 |
+--------------------+
1 row in set (0.00 sec)

mysql> select rand(2021);
+--------------------+
| rand(2021)         |
+--------------------+
| 0.7752841103591808 |
+--------------------+
1 row in set (0.00 sec)