鱼C论坛

 找回密码
 立即注册
查看: 2492|回复: 14

[已解决]隨機數種子的範圍

[复制链接]
发表于 2022-5-16 21:51:09 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
本帖最后由 一隻太平洋睡鯊 于 2022-5-16 21:53 编辑

在前一個問題帖
收到了這個答覆
https://www.zhihu.com/question/3 ... D%E8%A8%80%E6%88%96,ND_SEED%E3%80%82
在這裡面有寫到
"1) 首先给srand()提供一个种子,它是一个unsigned int类型,其取值范围从0~65535;"
我的教材也寫種子是一個無號整數
可是教材內對於無號型態的介紹是這樣
是不是教材有寫錯...?
到底無號整數(unsigned int)的範圍是多少?
0-65535的名稱到底叫啥?
隨機數種子的範圍是多少?
無號整數(unsigned int)和無號長整數(unsigned long int)的範圍確實一樣?
最佳答案
2022-5-17 10:40:05
一隻太平洋睡鯊 发表于 2022-5-17 10:24
這麼說來,隨機種子的內容,不是由C語言本身決定,而是由編譯器來決定的?
即使視同一個數值的隨機種 ...

這麼說來,隨機種子的內容,不是由C語言本身決定,而是由編譯器來決定的?
C語言标准没有规定int的大小,int的大小是由编译器的作者决定的

即使視同一個數值的隨機種子(比如srand(1))
也有可能因為編譯器的不同,而呈現不一樣的算法嗎?
这我就不知道了,我没有研究过这部分的内容
就算是随机算法一样,隨機種子的范围不一样,我想给出的结果应该也是不一样的

  1. $ cat main.c
  2. #include <stdio.h>
  3. #include <stdlib.h>

  4. int main(void) {
  5.     srand(1);
  6.     for(size_t i = 0; i < 10; ++i) {
  7.         printf("%d\n", rand());
  8.     }
  9.     return 0;
  10. }
  11. $ gcc -g -Wall -o main main.c
  12. $ ./main
  13. 1804289383
  14. 846930886
  15. 1681692777
  16. 1714636915
  17. 1957747793
  18. 424238335
  19. 719885386
  20. 1649760492
  21. 596516649
  22. 1189641421
  23. $ ./main
  24. 1804289383
  25. 846930886
  26. 1681692777
  27. 1714636915
  28. 1957747793
  29. 424238335
  30. 719885386
  31. 1649760492
  32. 596516649
  33. 1189641421
  34. $ ./main
  35. 1804289383
  36. 846930886
  37. 1681692777
  38. 1714636915
  39. 1957747793
  40. 424238335
  41. 719885386
  42. 1649760492
  43. 596516649
  44. 1189641421
  45. $ clang -g -Wall -o main main.c
  46. $ ./main
  47. 1804289383
  48. 846930886
  49. 1681692777
  50. 1714636915
  51. 1957747793
  52. 424238335
  53. 719885386
  54. 1649760492
  55. 596516649
  56. 1189641421
  57. $ ./main
  58. 1804289383
  59. 846930886
  60. 1681692777
  61. 1714636915
  62. 1957747793
  63. 424238335
  64. 719885386
  65. 1649760492
  66. 596516649
  67. 1189641421
  68. $ ./main
  69. 1804289383
  70. 846930886
  71. 1681692777
  72. 1714636915
  73. 1957747793
  74. 424238335
  75. 719885386
  76. 1649760492
  77. 596516649
  78. 1189641421
  79. $
复制代码


1.png
2.png
281401333_525422715746931_3977268785783129554_n.jpg
280301419_1811339602409556_5166861492876378140_n.jpg
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2022-5-16 22:03:20 | 显示全部楼层
是的,教材中写的是错误的
标准只规定了char是一个字节,其他的都没有规定
int并不是4个字节
long可以和int一样,也可以和int不一样

  1. $ cat main.c
  2. #include <stdio.h>

  3. int main(void) {
  4.     printf("%d\n", (int)sizeof(int));
  5.     printf("%d\n", (int)sizeof(long));
  6.     return 0;
  7. }
  8. $ gcc -g -Wall -o main main.c
  9. $ ./main
  10. 4
  11. 8
  12. $ gcc -m32 -g -Wall -o main main.c
  13. $ ./main
  14. 4
  15. 4
  16. $
复制代码

评分

参与人数 1荣誉 +1 鱼币 +1 贡献 +1 收起 理由
一隻太平洋睡鯊 + 1 + 1 + 1 感謝回覆

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-5-16 22:08:58 | 显示全部楼层
tc给出的结果是
int 是 2
long 是 4
标准只规定了char是一个字节,其他的都没有规定

1.png
2.png

评分

参与人数 1荣誉 +1 鱼币 +1 贡献 +1 收起 理由
一隻太平洋睡鯊 + 1 + 1 + 1 感謝回覆

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2022-5-16 22:42:33 | 显示全部楼层
人造人 发表于 2022-5-16 22:08
tc给出的结果是
int 是 2
long 是 4

字節=位元嗎?
2(字節/位元)是0~65535?
4(字節/位元)是0-4294967295?
所以
無號整數(unsigned int)的範圍是0~65535?
0-65535的名稱可以是無號整數(unsigned int)或無號短整數(unsigned short int)?
還是沒有無號短整數(unsigned short int)這個詞?
隨機數種子的範圍是0~65535?
無號整數(unsigned int)和無號長整數(unsigned long int)的範圍不一樣?
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-5-16 23:08:36 | 显示全部楼层
一隻太平洋睡鯊 发表于 2022-5-16 22:42
字節=位元嗎?
2(字節/位元)是0~65535?
4(字節/位元)是0-4294967295?

字節=位元,应该是这样的,我们这边叫字节,你们那边应该就是位元
1个字节是8位,2^8(2的8次方)是256,取值范围就是0~255
2个字节就是16位,就是2^16,就是65536,取值范围就是0~65535
4个字节就是2^32,就是4294967296,取值范围就是0~4294967295
unsigned int不是0~65535,这要看int是多少字节,如果int是2个字节,unsinged int就是0~65535
如果int是4个字节,unsinged int就是0~4294967295,如果int是一个字节,unsinged int就是0~255
问题是不知道int是多少个字节,也就不知道int的取值范围,当然也就不知道unsigned int的范围
隨機數種子的范围不是0~65535,隨機數種子的范围就是unsigned int的范围
不知道unsinged int的范围是多少,也就不知道隨機數種子的范围
unsigned int 和 unsigned long int 的范围可以一样,也可以不一样,标准没有规定这个,这个具体是有编译器的作者来决定的,编译器的作者可以选择让这两个一样,也可以让这两个不一样
标准只规定了char是一个字节,其他的都没有规定
使用sizeof运算符可以得到其他类型的大小

评分

参与人数 1荣誉 +5 鱼币 +5 贡献 +3 收起 理由
一隻太平洋睡鯊 + 5 + 5 + 3 鱼C有你更精彩^_^

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-5-16 23:12:04 | 显示全部楼层
不同的编译器,甚至是同一个编译器,不同的编译选项,只有char是一样的,是1
其他类型可以一样,也可以不一样
  1. $ cat main.c
  2. #include <stdio.h>

  3. int main(void) {
  4.     printf("%d\n", (int)sizeof(char));
  5.     printf("%d\n", (int)sizeof(short));
  6.     printf("%d\n", (int)sizeof(int));
  7.     printf("%d\n", (int)sizeof(long));
  8.     printf("%d\n", (int)sizeof(long long));
  9.     printf("%d\n", (int)sizeof(float));
  10.     printf("%d\n", (int)sizeof(double));
  11.     return 0;
  12. }
  13. $ gcc -g -Wall -o main main.c
  14. $ ./main
  15. 1
  16. 2
  17. 4
  18. 8
  19. 8
  20. 4
  21. 8
  22. $ gcc -m32 -g -Wall -o main main.c
  23. $ ./main
  24. 1
  25. 2
  26. 4
  27. 4
  28. 8
  29. 4
  30. 8
  31. $
复制代码

评分

参与人数 1荣誉 +1 鱼币 +1 贡献 +1 收起 理由
一隻太平洋睡鯊 + 1 + 1 + 1 感謝回覆

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-5-16 23:15:50 | 显示全部楼层
1.png
2.png

评分

参与人数 1荣誉 +1 鱼币 +1 贡献 +1 收起 理由
一隻太平洋睡鯊 + 1 + 1 + 1 感謝回覆

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2022-5-17 09:50:00 | 显示全部楼层
人造人 发表于 2022-5-16 23:08
字節=位元,应该是这样的,我们这边叫字节,你们那边应该就是位元
1个字节是8位,2^8(2的8次方)是256, ...

所以隨機種子是沒有範圍的?
任何4294967295以內的正整數都能夠放進srand()裡面?
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-5-17 09:54:49 | 显示全部楼层
一隻太平洋睡鯊 发表于 2022-5-17 09:50
所以隨機種子是沒有範圍的?
任何4294967295以內的正整數都能夠放進srand()裡面?

有范围,范围就是unsigned int的范围
sizeof(unsigned int) 得到 unsigned int的大小
知道了unsigned int的大小就知道了unsigned int的范围,就知道了隨機種子的范围

评分

参与人数 1荣誉 +1 鱼币 +1 贡献 +1 收起 理由
一隻太平洋睡鯊 + 1 + 1 + 1 感謝回覆

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2022-5-17 10:01:13 | 显示全部楼层
人造人 发表于 2022-5-17 09:54
有范围,范围就是unsigned int的范围
sizeof(unsigned int) 得到 unsigned int的大小
知道了unsigned i ...

我用了這個代碼,輸出是4,就是0~4294967295?
所以我開頭放的那個網站裡面寫的是錯的?
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-5-17 10:13:55 | 显示全部楼层
  1. $ cat main.c
  2. #include <stdio.h>

  3. int main(void) {
  4.     printf("%zu\n", sizeof(unsigned int));
  5.     return 0;
  6. }
  7. $ gcc -g -Wall -o main main.c
  8. $ ./main
  9. 4
  10. $ gcc --version
  11. gcc (GCC) 11.2.0
  12. Copyright (C) 2021 Free Software Foundation, Inc.
  13. This is free software; see the source for copying conditions.  There is NO
  14. warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

  15. $
复制代码


1.png
2.png
3.png


编译器不一样,int的大小有可能就不一样
即使是同一个编译器,不同的编译选项也可能影响int的大小

gcc版本是 11.2.0,编译选项是-g -Wall
给出的结果是4个字节,那么unsigned int的范围就是0~4294967295,隨機種子的范围就是0~4294967295

tc的版本是3.0,编译选项用的默认的
给出的结果是2个字节,那么unsigned int的范围就是0~65535,隨機種子的范围就是0~65535


想知道隨機種子的范围,得先知道unsigned int的范围
想知道unsigned int的范围,得先知道unsigned int的大小
用sizeof运算符可以得到unsigned int的大小
知道了unsigned int的大小,就知道了unsigned int的范围
知道了unsigned int的范围,就知道了隨機種子的范围
就是这样

评分

参与人数 1荣誉 +5 鱼币 +5 贡献 +3 收起 理由
一隻太平洋睡鯊 + 5 + 5 + 3 鱼C有你更精彩^_^

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-5-17 10:19:34 | 显示全部楼层
要看你定义的变量类型,int整形的话就是32767。
1) 首先给srand()提供一个种子,它是一个unsigned int类型,其取值范围从0~65535;
2) 然后调用rand(),它会根据提供给srand()的种子值返回一个随机数(在0到32767之间)

这些都是错误的,因为int整形不一定是32767, unsigned int类型取值范围也不一定是0~65535

评分

参与人数 1荣誉 +1 鱼币 +1 贡献 +1 收起 理由
一隻太平洋睡鯊 + 1 + 1 + 1 鱼C有你更精彩^_^

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2022-5-17 10:24:20 | 显示全部楼层
人造人 发表于 2022-5-17 10:19
要看你定义的变量类型,int整形的话就是32767。
1) 首先给srand()提供一个种子,它是一个unsigned int类型 ...
编译器不一样,int的大小有可能就不一样
即使是同一个编译器,不同的编译选项也可能影响int的大小

這麼說來,隨機種子的內容,不是由C語言本身決定,而是由編譯器來決定的?
即使視同一個數值的隨機種子(比如srand(1))
也有可能因為編譯器的不同,而呈現不一樣的算法嗎?
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-5-17 10:25:52 | 显示全部楼层
  1. rand()会返回一随机数值,范围在0至RAND_MAX 间。返回0至RAND_MAX之间的随机数值,RAND_MAX定义在stdlib.h,(其值至少为32767),运算的结果是一个不定的数,要看你定义的变量类型,int整形的话就是32767。 在调用此函数产生随机数前,必须先利用srand()设好随机数种子,如果未设随机数种子,rand()在调用时会自动设随机数种子为1。一般用for语句来设置种子的个数。具体见下面的例子。
复制代码

  1. $ cat main.c
  2. #include <stdio.h>
  3. #include <stdlib.h>

  4. int main(void) {
  5.     printf("%u\n", RAND_MAX);
  6.     return 0;
  7. }
  8. $ gcc -g -Wall -o main main.c
  9. $ ./main
  10. 2147483647
  11. $
复制代码


1.png
2.png


评分

参与人数 1贡献 +1 收起 理由
一隻太平洋睡鯊 + 1 鱼C有你更精彩^_^

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-5-17 10:40:05 | 显示全部楼层    本楼为最佳答案   
一隻太平洋睡鯊 发表于 2022-5-17 10:24
這麼說來,隨機種子的內容,不是由C語言本身決定,而是由編譯器來決定的?
即使視同一個數值的隨機種 ...

這麼說來,隨機種子的內容,不是由C語言本身決定,而是由編譯器來決定的?
C語言标准没有规定int的大小,int的大小是由编译器的作者决定的

即使視同一個數值的隨機種子(比如srand(1))
也有可能因為編譯器的不同,而呈現不一樣的算法嗎?
这我就不知道了,我没有研究过这部分的内容
就算是随机算法一样,隨機種子的范围不一样,我想给出的结果应该也是不一样的

  1. $ cat main.c
  2. #include <stdio.h>
  3. #include <stdlib.h>

  4. int main(void) {
  5.     srand(1);
  6.     for(size_t i = 0; i < 10; ++i) {
  7.         printf("%d\n", rand());
  8.     }
  9.     return 0;
  10. }
  11. $ gcc -g -Wall -o main main.c
  12. $ ./main
  13. 1804289383
  14. 846930886
  15. 1681692777
  16. 1714636915
  17. 1957747793
  18. 424238335
  19. 719885386
  20. 1649760492
  21. 596516649
  22. 1189641421
  23. $ ./main
  24. 1804289383
  25. 846930886
  26. 1681692777
  27. 1714636915
  28. 1957747793
  29. 424238335
  30. 719885386
  31. 1649760492
  32. 596516649
  33. 1189641421
  34. $ ./main
  35. 1804289383
  36. 846930886
  37. 1681692777
  38. 1714636915
  39. 1957747793
  40. 424238335
  41. 719885386
  42. 1649760492
  43. 596516649
  44. 1189641421
  45. $ clang -g -Wall -o main main.c
  46. $ ./main
  47. 1804289383
  48. 846930886
  49. 1681692777
  50. 1714636915
  51. 1957747793
  52. 424238335
  53. 719885386
  54. 1649760492
  55. 596516649
  56. 1189641421
  57. $ ./main
  58. 1804289383
  59. 846930886
  60. 1681692777
  61. 1714636915
  62. 1957747793
  63. 424238335
  64. 719885386
  65. 1649760492
  66. 596516649
  67. 1189641421
  68. $ ./main
  69. 1804289383
  70. 846930886
  71. 1681692777
  72. 1714636915
  73. 1957747793
  74. 424238335
  75. 719885386
  76. 1649760492
  77. 596516649
  78. 1189641421
  79. $
复制代码


1.png
2.png

评分

参与人数 2荣誉 +11 鱼币 +11 贡献 +9 收起 理由
Twilight6 + 6 + 6 + 6 鱼C有你更精彩^_^
一隻太平洋睡鯊 + 5 + 5 + 3 看來要理解這方面還需要更深入,對新手來說.

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2025-4-25 21:57

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表