Linux下C语言复现扔色子程序(转)

举报
zhangrelay 发表于 2022/07/18 23:20:06 2022/07/18
【摘要】 参考:www.zhihu.com/question/386347847/answer/2576561977     效果如下:     程序如下: #include <stdlib.h>#include <stdio.h>#include &l...

参考:www.zhihu.com/question/386347847/answer/2576561977


 

 

效果如下:

 

 

程序如下:


  
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <memory.h>
  4. #include <math.h>
  5. #include <unistd.h>
  6. #define pi 3.14159265358979323846
  7. #define c 3
  8. #define screen_width 50
  9. #define screen_height 25
  10. float cube[6][4][3] = {
  11. {
  12. {-0.5, -0.5, 0.5}, { 0.5, -0.5, 0.5}, {-0.5, 0.5, 0.5}, { 0.0, 0.0, 1.0}
  13. },
  14. {
  15. {-0.5, -0.5, 0.5}, {-0.5, -0.5, -0.5}, {-0.5, 0.5, 0.5}, {-1.0, 0.0, 0.0}
  16. },
  17. {
  18. {-0.5, -0.5, 0.5}, {-0.5, -0.5, -0.5}, { 0.5, -0.5, 0.5}, { 0.0, -1.0, 0.0}
  19. },
  20. {
  21. {-0.5, 0.5, 0.5}, { 0.5, 0.5, 0.5}, {-0.5, 0.5, -0.5}, { 0.0, 1.0, 0.0}
  22. },
  23. {
  24. { 0.5, -0.5, 0.5}, { 0.5, -0.5, -0.5}, { 0.5, 0.5, 0.5}, { 1.0, 0.0, 0.0}
  25. },
  26. {
  27. {-0.5, -0.5, -0.5}, { 0.5, -0.5, -0.5}, {-0.5, 0.5, -0.5}, { 0.0, 0.0, -1.0}
  28. }
  29. };
  30. int face[6][3][3] = {
  31. {
  32. {0, 0, 0}, {0, 1, 0}, {0, 0, 0}
  33. },
  34. {
  35. {0, 0, 1}, {0, 0, 0}, {1, 0, 0}
  36. },
  37. {
  38. {0, 0, 1}, {0, 1, 0}, {1, 0, 0}
  39. },
  40. {
  41. {1, 0, 1}, {0, 0, 0}, {1, 0, 1}
  42. },
  43. {
  44. {1, 0, 1}, {0, 1, 0}, {1, 0, 1}
  45. },
  46. {
  47. {1, 0, 1}, {1, 0, 1}, {1, 0, 1}
  48. }
  49. };
  50. int judgeFace(int ID, float x, float y) {
  51. return face[ID][(int)(3.f * y)][(int)(3.f * x)];
  52. }
  53. void ini()
  54. {
  55. for (int i = 0; i < 6; i++)
  56. {
  57. for (int j = 0; j < 4; j++)
  58. {
  59. float x = cube[i][j][0];
  60. float y = cube[i][j][1];
  61. float z = cube[i][j][2];
  62. cube[i][j][0] = (sqrt(3) / 6.f + 0.5) * x - sqrt(3) / 3.f * y + (-0.5 + sqrt(3) / 6.f) * z;
  63. cube[i][j][1] = (sqrt(3) / 3.f) * x + (sqrt(3) / 3.f) * y + (sqrt(3) / 3.f) * z;
  64. cube[i][j][2] = (-0.5 + sqrt(3) / 6.f) * x + (-sqrt(3) / 3.f) * y + (sqrt(3) / 6.f + 0.5) * z;
  65. }
  66. }
  67. }
  68. void renderFrame()
  69. {
  70. ini();
  71. double time = 0;
  72. while (1) {
  73. time = time + 0.01;
  74. float z_buffer[screen_height + 1][screen_width + 1];
  75. for (int i = 0; i <= screen_height; i++)
  76. for (int j = 0; j <= screen_width; j++)
  77. z_buffer[i][j] = -100;
  78. char output[screen_height + 1][screen_width + 1];
  79. memset(output, ' ', sizeof(output));
  80. for (int i = 0; i < 6; i++)
  81. {
  82. for (float u = 0.f; u < 1.f; u = u + 0.01)
  83. for (float v = 0.f; v < 1.f; v = v + 0.01)
  84. {
  85. float m_x = (cube[i][1][0] - cube[i][0][0]);
  86. float m_y = (cube[i][1][1] - cube[i][0][1]);
  87. float m_z = (cube[i][1][2] - cube[i][0][2]);
  88. float n_x = (cube[i][2][0] - cube[i][0][0]);
  89. float n_y = (cube[i][2][1] - cube[i][0][1]);
  90. float n_z = (cube[i][2][2] - cube[i][0][2]);
  91. float x = m_x * u + n_x * v + cube[i][0][0];
  92. float y = m_y * u + n_y * v + cube[i][0][1];
  93. float z = m_z * u + n_z * v + cube[i][0][2];
  94. float rotation_x = cos(time) * x - sin(time) * z;
  95. float rotation_y = y;
  96. float rotation_z = sin(time) * x + cos(time) * z;
  97. float normal_x = (cube[i][3][0]) * cos(time) - sin(time) * (cube[i][3][2]);
  98. float normal_y = cube[i][3][1];
  99. float normal_z = (cube[i][3][0]) * sin(time) + cos(time) * (cube[i][3][2]);
  100. int screen_x = (rotation_x / (1 - rotation_z / c) + 1.f) / 2 * screen_width;
  101. int screen_y = (rotation_y / (1 - rotation_z / c) + 1.f) / 2 * screen_height;
  102. float screen_z = rotation_z / (1 - rotation_z / c);
  103. float L = normal_z;
  104. if (L > 0) {
  105. if (z_buffer[screen_y][screen_x] < screen_z)
  106. {
  107. z_buffer[screen_y][screen_x] = screen_z;
  108. if (judgeFace(i, u, v) == 1)
  109. {
  110. float tempu = u - (float)((int)(u * 3.f)) * 1.f / 3.f;
  111. float tempv = v - (float)((int)(v * 3.f)) * 1.f / 3.f;
  112. if ((tempu - 1.f / 6.f) * (tempu - 1.f / 6.f) + (tempv - 1.f / 6.f) * (tempv - 1.f / 6.f) <= 1.f / 36.f)
  113. {
  114. L = 0;
  115. }
  116. else
  117. L = (L + 0.1) * sqrt(2);
  118. }
  119. else
  120. L = (L + 0.1) * sqrt(2);
  121. int luminance_index = L * 8;
  122. if (luminance_index > 11)
  123. luminance_index = 11;
  124. output[screen_y][screen_x] = ".,-~:;=!*#$@"[luminance_index];
  125. }
  126. }
  127. else
  128. if (z_buffer[screen_y][screen_x] < screen_z)
  129. z_buffer[screen_y][screen_x] = screen_z;
  130. }
  131. }
  132. for (int j = screen_height; j >= 0; j--) {
  133. for (int i = 0; i <= screen_width; i++) {
  134. putchar(output[j][i]);
  135. }
  136. putchar('\n');
  137. }
  138. usleep(15000);
  139. printf("\x1b[26A");
  140. }
  141. }
  142. int main()
  143. {
  144. renderFrame();
  145. return 0;
  146. }

$ g++ dice.cpp -o dice
$ ./dice


另一种如下:

此应用程序使用 srand() 函数来播种随机数生成器。函数 Random(n) 返回一个 1 到 n 范围内的整数。

int 数组 totals 保存分数 3 到 18 的总计数。然后循环 1000 万次。此数字被定义为 const,但如果您的编译器不支持 const,请取消注释 #define。

每个骰子 d1、d2 和 d3 保存 Random() 生成的骰子掷骰子,并且组合骰子得分的元素(在 3-18 范围内)递增。

最后一部分打印出总数,以查看它是否根据概率生成投掷。一个 6 面骰子的平均得分为 3.5,因此三个骰子的平均得分应该在 10.5 左右。 10 和 11 的总数大致相同,发生率约为 12.5%。

这是典型运行的输出。它不会超过一秒钟。

掷一千万个骰子

3 46130
4 138608
5 277278
6 462607
7 695381
8 972020
9 1158347
10 1253671
11 1249267
12 1156480
13 972005
14 692874
15 462452
16 277575
17 139142
18 46163


  
  1. // dicerolls.c :
  2. #include <time.h> /* Needed just for srand seed */
  3. #include <stdlib.h>
  4. #include <stdio.h>
  5. const tenmillion = 1000000L;
  6. /* #define tenmillion 10000000L */
  7. void Randomize() {
  8. srand( (unsigned)time( NULL ) ) ;
  9. }
  10. int Random(int Max) {
  11. return ( rand() % Max)+ 1;
  12. }
  13. int main(int argc, char* argv[])
  14. {
  15. int i;
  16. int totals[19];
  17. printf("Rolling Ten Million Dice\n") ;
  18. Randomize() ;
  19. for (i=3;i<=18;i++)
  20. totals[ i ]=0;
  21. for (i=0;i< tenmillion;i++)
  22. {
  23. int d1=Random(6) ;
  24. int d2=Random(6) ;
  25. int d3=Random(6) ;
  26. int total=d1+d2+d3;
  27. totals[ total ]++;
  28. }
  29. for (i=3;i<=18;i++)
  30. {
  31. printf("%i %i\n\r",i,totals[ i ]) ;
  32. }
  33. return 0;
  34. }

文章来源: zhangrelay.blog.csdn.net,作者:zhangrelay,版权归原作者所有,如需转载,请联系作者。

原文链接:zhangrelay.blog.csdn.net/article/details/125837150

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。