/specs/math/random.ds

http://github.com/wilkie/djehuty · Unknown · 210 lines · 180 code · 30 blank · 0 comment · 0 complexity · a1da2c26f08ae47316490b5f6ea83097 MD5 · raw file

  1. module specs.math.random;
  2. import testing.support;
  3. import math.random;
  4. import data.iterable;
  5. import data.list;
  6. describe random() {
  7. const uint SEED = 12345678;
  8. const uint REPEATS = 1000000;
  9. describe creation() {
  10. it should_have_sane_defaults() {
  11. auto r = new Random();
  12. should(r.seed >= 0);
  13. }
  14. it should_not_reuse_a_seed() {
  15. auto a = new Random();
  16. auto b = new Random();
  17. shouldNot(a.seed == b.seed);
  18. }
  19. it should_use_the_given_seed() {
  20. auto r = new Random(SEED);
  21. should(r.seed == SEED);
  22. }
  23. }
  24. describe state() {
  25. it should_be_reproducible() {
  26. auto a = new Random(SEED);
  27. auto b = new Random(SEED);
  28. should(a.next() == b.next());
  29. }
  30. }
  31. describe seed() {
  32. it should_set_and_get_the_seed() {
  33. auto r = new Random();
  34. r.seed = SEED;
  35. should(r.seed == SEED);
  36. }
  37. }
  38. // TODO: Statistical tests should be implemented for all the "next" methods.
  39. describe next() {
  40. it should_not_be_stuck() {
  41. auto r = new Random();
  42. shouldNot(r.next() == r.next());
  43. }
  44. it should_return_zero_if_upper_bound_is_zero() {
  45. auto r = new Random();
  46. should(r.next(0) == 0);
  47. }
  48. it should_return_a_nonnegative_value_less_than_upper_bound() {
  49. auto r = new Random();
  50. uint v;
  51. uint upper = 1;
  52. for (uint i = 0; i < REPEATS; i++) {
  53. v = r.next(upper);
  54. should(v >= 0);
  55. should(v < upper);
  56. upper += i;
  57. }
  58. }
  59. it should_return_greatest_bound_if_bounds_overlap() {
  60. auto r = new Random();
  61. should(r.next(0, 0) == 0);
  62. should(r.next(123, 123) == 123);
  63. should(r.next(-123, -123) == -123);
  64. should(r.next(123, -123) == 123);
  65. }
  66. it should_return_a_value_within_bounds() {
  67. auto r = new Random();
  68. int v;
  69. int lower = 0;
  70. int upper = 1;
  71. for (uint i = 0; i < REPEATS; i++) {
  72. v = r.next(lower, upper);
  73. should(v >= lower);
  74. should(v < upper);
  75. lower -= 12;
  76. upper += 3;
  77. }
  78. }
  79. }
  80. describe nextLong() {
  81. it should_not_be_stuck() {
  82. auto r = new Random();
  83. shouldNot(r.nextLong() == r.nextLong());
  84. }
  85. it should_return_zero_if_upper_bound_is_zero() {
  86. auto r = new Random();
  87. should(r.nextLong(0) == 0);
  88. }
  89. it should_return_a_nonnegative_value_less_than_upper_bound() {
  90. auto r = new Random();
  91. ulong v;
  92. ulong upper = 1;
  93. for (uint i = 0; i < REPEATS; i++) {
  94. v = r.nextLong(upper);
  95. should(v >= 0);
  96. should(v < upper);
  97. upper += i;
  98. }
  99. }
  100. it should_return_greatest_bound_if_bounds_overlap() {
  101. auto r = new Random();
  102. should(r.nextLong(0, 0) == 0);
  103. should(r.nextLong(123, 123) == 123);
  104. should(r.nextLong(-123, -123) == -123);
  105. should(r.nextLong(123, -123) == 123);
  106. }
  107. it should_return_a_value_within_bounds() {
  108. auto r = new Random();
  109. long v;
  110. long lower = 0;
  111. long upper = 1;
  112. for (uint i = 0; i < REPEATS; i++) {
  113. v = r.nextLong(lower, upper);
  114. should(v >= lower);
  115. should(v < upper);
  116. lower -= i;
  117. upper += 2*i;
  118. }
  119. }
  120. }
  121. describe nextBoolean() {
  122. it should_return_a_boolean() {
  123. auto r = new Random();
  124. bool to_be = r.nextBoolean();
  125. should(to_be || !to_be);
  126. }
  127. }
  128. describe nextDouble() {
  129. it should_return_a_value_between_0_and_1() {
  130. auto r = new Random();
  131. double v;
  132. for (uint i = 0; i < REPEATS; i++) {
  133. v = r.nextDouble();
  134. should(v >= 0.0);
  135. should(v <= 1.0);
  136. }
  137. }
  138. }
  139. describe nextFloat() {
  140. it should_return_a_value_between_0_and_1() {
  141. auto r = new Random();
  142. double v;
  143. for (uint i = 0; i < REPEATS; i++) {
  144. v = r.nextFloat();
  145. should(v >= 0.0);
  146. should(v <= 1.0);
  147. }
  148. }
  149. }
  150. describe choose() {
  151. it should_fail_on_empty_list() {
  152. auto r = new Random();
  153. shouldThrow();
  154. r.choose(new List!(uint));
  155. }
  156. it should_return_the_item_given_one() {
  157. auto r = new Random();
  158. uint[] arr = [1234];
  159. should(r.choose(arr) == 1234);
  160. }
  161. it should_work_for_arrays() {
  162. auto r = new Random();
  163. uint[] arr = [2, 5, 6, 9, 10, 13];
  164. uint v;
  165. for (uint i = 0; i < REPEATS; i++) {
  166. v = r.choose(arr);
  167. shouldNot(member(v, arr) is null);
  168. }
  169. }
  170. it should_work_for_lists() {
  171. auto r = new Random();
  172. List!(char) lst = new List!(char)(['a', 'e', 'i', 'o', 'u']);
  173. char v;
  174. for (uint i = 0; i < REPEATS; i++) {
  175. v = r.choose(lst);
  176. shouldNot(member(v, lst) is null);
  177. }
  178. }
  179. }
  180. }