trackler 2.0.0.1 → 2.0.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (226) hide show
  1. checksums.yaml +4 -4
  2. data/bin/bump-content +3 -1
  3. data/bin/verify-metadata +2 -2
  4. data/common/exercises/alphametics/canonical-data.json +19 -9
  5. data/common/exercises/food-chain/canonical-data.json +7 -1
  6. data/common/exercises/grains/canonical-data.json +66 -0
  7. data/common/exercises/raindrops/description.md +4 -5
  8. data/common/exercises/triangle/canonical-data.json +81 -54
  9. data/lib/trackler/version.rb +1 -1
  10. data/tracks/c/config.json +26 -19
  11. data/tracks/c/exercises/allergies/makefile +15 -0
  12. data/tracks/c/exercises/allergies/src/allergies.h +21 -0
  13. data/tracks/c/exercises/allergies/src/example.c +32 -0
  14. data/tracks/c/exercises/allergies/src/example.h +26 -0
  15. data/tracks/c/exercises/allergies/test/test_allergies.c +203 -0
  16. data/tracks/c/exercises/allergies/test/vendor/unity.c +1300 -0
  17. data/tracks/c/exercises/allergies/test/vendor/unity.h +274 -0
  18. data/tracks/c/exercises/allergies/test/vendor/unity_internals.h +701 -0
  19. data/tracks/c/exercises/atbash-cipher/makefile +16 -0
  20. data/tracks/c/exercises/atbash-cipher/src/example.c +71 -0
  21. data/tracks/c/exercises/atbash-cipher/src/example.h +7 -0
  22. data/tracks/c/exercises/atbash-cipher/test/test_atbash_cipher.c +113 -0
  23. data/tracks/c/exercises/atbash-cipher/test/vendor/unity.c +1300 -0
  24. data/tracks/c/exercises/atbash-cipher/test/vendor/unity.h +274 -0
  25. data/tracks/c/exercises/atbash-cipher/test/vendor/unity_internals.h +701 -0
  26. data/tracks/c/exercises/phone-number/makefile +16 -0
  27. data/tracks/c/exercises/phone-number/src/example.c +66 -0
  28. data/tracks/c/exercises/phone-number/src/example.h +8 -0
  29. data/tracks/c/exercises/phone-number/test/test_phone_number.c +108 -0
  30. data/tracks/c/exercises/phone-number/test/vendor/unity.c +1300 -0
  31. data/tracks/c/exercises/phone-number/test/vendor/unity.h +274 -0
  32. data/tracks/c/exercises/phone-number/test/vendor/unity_internals.h +701 -0
  33. data/tracks/csharp/config.json +8 -0
  34. data/tracks/csharp/exercises/bowling/BowlingTest.cs +188 -33
  35. data/tracks/csharp/exercises/bowling/Example.cs +38 -9
  36. data/tracks/csharp/exercises/rectangles/Example.cs +91 -0
  37. data/tracks/csharp/exercises/rectangles/RectanglesTest.cs +133 -0
  38. data/tracks/elisp/docs/INSTALLATION.org +1 -1
  39. data/tracks/elixir/config.json +8 -66
  40. data/tracks/elixir/docs/LEARNING.md +1 -1
  41. data/tracks/elixir/exercises/diamond/diamond_test.exs +12 -12
  42. data/tracks/elixir/exercises/grep/example.exs +92 -0
  43. data/tracks/elixir/exercises/grep/grep.exs +6 -0
  44. data/tracks/elixir/exercises/grep/grep_test.exs +259 -0
  45. data/tracks/elixir/exercises/markdown/markdown.exs +59 -2
  46. data/tracks/elixir/exercises/nucleotide-count/nucleotide_count_test.exs +4 -4
  47. data/tracks/elixir/exercises/phone-number/phone_number_test.exs +5 -0
  48. data/tracks/fsharp/exercises/bowling/BowlingTest.fs +158 -43
  49. data/tracks/fsharp/exercises/bowling/Example.fs +53 -24
  50. data/tracks/go/config.json +5 -0
  51. data/tracks/go/exercises/diamond/diamond_test.go +227 -0
  52. data/tracks/go/exercises/diamond/example.go +47 -0
  53. data/tracks/go/exercises/food-chain/example.go +1 -1
  54. data/tracks/go/exercises/food-chain/food_chain_test.go +30 -6
  55. data/tracks/go/exercises/nucleotide-count/example.go +21 -8
  56. data/tracks/go/exercises/nucleotide-count/nucleotide_count_test.go +45 -37
  57. data/tracks/haskell/exercises/anagram/test/Tests.hs +1 -11
  58. data/tracks/java/bin/journey-test.sh +165 -128
  59. data/tracks/java/docs/ABOUT.md +5 -8
  60. data/tracks/java/exercises/hello-world/build.gradle +0 -6
  61. data/tracks/java/exercises/hello-world/src/test/java/HelloWorldTest.java +0 -1
  62. data/tracks/java/exercises/meetup/build.gradle +0 -1
  63. data/tracks/java/exercises/meetup/src/example/java/Meetup.java +9 -7
  64. data/tracks/java/exercises/meetup/src/test/java/MeetupTest.java +185 -188
  65. data/tracks/lua/config.json +0 -73
  66. data/tracks/lua/exercises/bowling/bowling_spec.lua +92 -48
  67. data/tracks/lua/exercises/bowling/example.lua +4 -1
  68. data/tracks/objective-c/config.json +9 -30
  69. data/tracks/objective-c/exercises/pangram/PangramExample.h +7 -0
  70. data/tracks/objective-c/exercises/pangram/PangramExample.m +21 -0
  71. data/tracks/objective-c/exercises/pangram/PangramTest.m +51 -0
  72. data/tracks/objective-c/xcodeProject/ObjectiveC.xcodeproj/project.pbxproj +18 -0
  73. data/tracks/ocaml/README.md +46 -1
  74. data/tracks/ocaml/SETUP.md +21 -2
  75. data/tracks/ocaml/config.json +48 -78
  76. data/tracks/perl5/README.md +15 -8
  77. data/tracks/perl5/testall.pl +5 -5
  78. data/tracks/php/config.json +26 -34
  79. data/tracks/php/docs/ABOUT.md +15 -0
  80. data/tracks/php/exercises/allergies/allergies_test.php +121 -0
  81. data/tracks/php/exercises/allergies/example.php +64 -0
  82. data/tracks/php/exercises/etl/etl_test.php +52 -0
  83. data/tracks/php/exercises/etl/example.php +12 -0
  84. data/tracks/php/exercises/nucleotide-count/example.php +25 -0
  85. data/tracks/php/exercises/nucleotide-count/nucleotide-count_test.php +36 -0
  86. data/tracks/php/exercises/pig-latin/example.php +25 -29
  87. data/tracks/php/exercises/pig-latin/pig-latin_test.php +26 -19
  88. data/tracks/php/exercises/space-age/example.php +65 -0
  89. data/tracks/php/exercises/space-age/space-age_test.php +70 -0
  90. data/tracks/php/exercises/triangle/example.php +43 -0
  91. data/tracks/php/exercises/triangle/triangle_test.php +140 -0
  92. data/tracks/pony/exercises/anagram/example.pony +6 -6
  93. data/tracks/pony/exercises/anagram/test.pony +3 -4
  94. data/tracks/pony/exercises/bob/test.pony +23 -23
  95. data/tracks/pony/exercises/difference-of-squares/test.pony +11 -11
  96. data/tracks/pony/exercises/hamming/example.pony +3 -3
  97. data/tracks/pony/exercises/hamming/test.pony +16 -16
  98. data/tracks/pony/exercises/hello-world/test.pony +5 -4
  99. data/tracks/pony/exercises/leap/test.pony +8 -8
  100. data/tracks/python/config.json +18 -0
  101. data/tracks/python/exercises/diamond/diamond_test.py +33 -0
  102. data/tracks/python/exercises/diamond/example.py +15 -0
  103. data/tracks/python/exercises/linked-list/example.py +47 -0
  104. data/tracks/python/exercises/linked-list/linked_list.py +13 -0
  105. data/tracks/python/exercises/linked-list/linked_list_test.py +49 -0
  106. data/tracks/python/exercises/list-ops/example.py +55 -0
  107. data/tracks/python/exercises/list-ops/list_ops.py +38 -0
  108. data/tracks/python/exercises/list-ops/list_ops_test.py +136 -0
  109. data/tracks/ruby/bin/generate +22 -2
  110. data/tracks/ruby/config.json +12 -83
  111. data/tracks/ruby/exercises/allergies/allergies_test.rb +0 -1
  112. data/tracks/ruby/exercises/atbash-cipher/atbash_cipher_test.rb +0 -1
  113. data/tracks/ruby/exercises/beer-song/beer_song_test.rb +1 -2
  114. data/tracks/ruby/exercises/binary/example.rb +0 -1
  115. data/tracks/ruby/exercises/binary-search-tree/binary_search_tree_test.rb +1 -1
  116. data/tracks/ruby/exercises/bowling/.version +1 -0
  117. data/tracks/ruby/exercises/bowling/bowling_test.rb +109 -133
  118. data/tracks/ruby/exercises/bowling/example.rb +7 -7
  119. data/tracks/ruby/exercises/bowling/example.tt +27 -0
  120. data/tracks/ruby/exercises/circular-buffer/circular_buffer_test.rb +0 -2
  121. data/tracks/ruby/exercises/clock/example.rb +0 -2
  122. data/tracks/ruby/exercises/connect/connect_test.rb +0 -1
  123. data/tracks/ruby/exercises/custom-set/custom_set_test.rb +0 -1
  124. data/tracks/ruby/exercises/diamond/diamond_test.rb +0 -1
  125. data/tracks/ruby/exercises/etl/etl_test.rb +1 -1
  126. data/tracks/ruby/exercises/house/house_test.rb +0 -1
  127. data/tracks/ruby/exercises/isogram/isogram_test.rb +2 -2
  128. data/tracks/ruby/exercises/largest-series-product/example.tt +0 -3
  129. data/tracks/ruby/exercises/largest-series-product/largest_series_product_test.rb +0 -4
  130. data/tracks/ruby/exercises/linked-list/linked_list_test.rb +1 -1
  131. data/tracks/ruby/exercises/meetup/meetup_test.rb +0 -1
  132. data/tracks/ruby/exercises/nth-prime/example.tt +0 -2
  133. data/tracks/ruby/exercises/nth-prime/nth_prime_test.rb +0 -2
  134. data/tracks/ruby/exercises/ocr-numbers/ocr_numbers_test.rb +1 -2
  135. data/tracks/ruby/exercises/protein-translation/protein_translation_test.rb +0 -1
  136. data/tracks/ruby/exercises/proverb/proverb_test.rb +1 -3
  137. data/tracks/ruby/exercises/queen-attack/example.rb +3 -1
  138. data/tracks/ruby/exercises/queen-attack/queen_attack_test.rb +34 -8
  139. data/tracks/ruby/exercises/robot-simulator/robot_simulator_test.rb +1 -1
  140. data/tracks/ruby/exercises/strain/strain_test.rb +2 -2
  141. data/tracks/ruby/exercises/tournament/.version +1 -0
  142. data/tracks/ruby/exercises/tournament/example.rb +54 -0
  143. data/tracks/ruby/exercises/tournament/example.tt +23 -0
  144. data/tracks/ruby/exercises/tournament/tournament_test.rb +92 -0
  145. data/tracks/ruby/exercises/transpose/.version +1 -0
  146. data/tracks/ruby/exercises/transpose/example.rb +14 -0
  147. data/tracks/ruby/exercises/transpose/example.tt +22 -0
  148. data/tracks/ruby/exercises/transpose/transpose_test.rb +303 -0
  149. data/tracks/ruby/lib/bowling_cases.rb +46 -0
  150. data/tracks/ruby/lib/isogram_cases.rb +1 -1
  151. data/tracks/ruby/lib/tournament_cases.rb +45 -0
  152. data/tracks/ruby/lib/transpose_cases.rb +45 -0
  153. data/tracks/rust/config.json +2 -0
  154. data/tracks/rust/exercises/bowling/.gitignore +7 -0
  155. data/tracks/rust/exercises/bowling/Cargo.toml +3 -0
  156. data/tracks/rust/exercises/bowling/example.rs +134 -0
  157. data/tracks/rust/exercises/bowling/tests/bowling.rs +373 -0
  158. data/tracks/rust/exercises/grains/.gitignore +7 -0
  159. data/tracks/rust/exercises/grains/Cargo.toml +3 -0
  160. data/tracks/rust/exercises/grains/example.rs +11 -0
  161. data/tracks/rust/exercises/grains/src/lib.rs +7 -0
  162. data/tracks/rust/exercises/grains/tests/grains.rs +63 -0
  163. data/tracks/rust/problems.md +2 -0
  164. data/tracks/scala/README.md +38 -0
  165. data/tracks/scala/config.json +20 -74
  166. data/tracks/scala/exercises/accumulate/src/test/scala/accumulate_test.scala +4 -0
  167. data/tracks/scala/exercises/allergies/src/test/scala/allergies_test.scala +11 -0
  168. data/tracks/scala/exercises/alphametics/build.sbt +6 -0
  169. data/tracks/scala/exercises/alphametics/example.scala +125 -0
  170. data/tracks/scala/exercises/alphametics/src/main/scala/.keep +0 -0
  171. data/tracks/scala/exercises/alphametics/src/test/scala/AlphameticsTest.scala +62 -0
  172. data/tracks/scala/exercises/atbash-cipher/src/test/scala/atbash_test.scala +8 -0
  173. data/tracks/scala/exercises/bank-account/src/test/scala/BankAccountTest.scala +4 -0
  174. data/tracks/scala/exercises/binary/src/test/scala/binary_test.scala +13 -0
  175. data/tracks/scala/exercises/binary-search-tree/src/test/scala/BstTest.scala +11 -0
  176. data/tracks/scala/exercises/bowling/Example.scala +116 -0
  177. data/tracks/scala/exercises/bowling/build.sbt +3 -0
  178. data/tracks/scala/exercises/bowling/src/main/scala/Bowling.scala +11 -0
  179. data/tracks/scala/exercises/bowling/src/test/scala/BowlingSuite.scala +237 -0
  180. data/tracks/scala/exercises/clock/src/test/scala/ClockTest.scala +50 -0
  181. data/tracks/scala/exercises/connect/README.md +17 -0
  182. data/tracks/scala/exercises/connect/src/test/scala/ConnectTest.scala +7 -0
  183. data/tracks/scala/exercises/crypto-square/src/test/scala/{CrytpoSquareTest.scala → CryptoSquareTest.scala} +9 -0
  184. data/tracks/scala/exercises/custom-set/src/test/scala/CustomSetTest.scala +36 -0
  185. data/tracks/scala/exercises/difference-of-squares/src/test/scala/squares_test.scala +8 -0
  186. data/tracks/scala/exercises/forth/src/test/scala/ForthTest.scala +22 -0
  187. data/tracks/scala/exercises/hexadecimal/src/test/scala/HexadecimalTest.scala +8 -0
  188. data/tracks/scala/exercises/kindergarten-garden/src/test/scala/GardenTest.scala +5 -0
  189. data/tracks/scala/exercises/largest-series-product/src/test/scala/SeriesTest.scala +2 -0
  190. data/tracks/scala/exercises/linked-list/src/test/scala/DequeTest.scala +4 -0
  191. data/tracks/scala/exercises/luhn/src/test/scala/LuhnTest.scala +4 -0
  192. data/tracks/scala/exercises/matrix/src/test/scala/MatrixTest.scala +2 -0
  193. data/tracks/scala/exercises/minesweeper/src/test/scala/MinesweeperTest.scala +6 -0
  194. data/tracks/scala/exercises/nth-prime/src/test/scala/PrimeTest.scala +5 -0
  195. data/tracks/scala/exercises/ocr-numbers/src/test/scala/OcrTest.scala +15 -0
  196. data/tracks/scala/exercises/octal/src/test/scala/OctalTest.scala +7 -0
  197. data/tracks/scala/exercises/parallel-letter-frequency/src/test/scala/FrequencyTest.scala +8 -0
  198. data/tracks/scala/exercises/pascals-triangle/src/test/scala/PascalsTriangleTest.scala +5 -0
  199. data/tracks/scala/exercises/pig-latin/src/test/scala/PigLatinTest.scala +4 -0
  200. data/tracks/scala/exercises/pythagorean-triplet/src/test/scala/PythagoreanTripletTest.scala +3 -0
  201. data/tracks/scala/exercises/queen-attack/src/test/scala/QueensTest.scala +5 -0
  202. data/tracks/scala/exercises/robot-simulator/src/test/scala/RobotTest.scala +16 -8
  203. data/tracks/scala/exercises/say/src/test/scala/SayTest.scala +34 -17
  204. data/tracks/scala/exercises/scrabble-score/src/test/scala/scrabble_score_test.scala +6 -0
  205. data/tracks/scala/exercises/secret-handshake/src/test/scala/SecretHandshakeTest.scala +18 -9
  206. data/tracks/scala/exercises/series/src/test/scala/SeriesTest.scala +4 -2
  207. data/tracks/scala/exercises/sieve/src/test/scala/SieveTest.scala +8 -4
  208. data/tracks/scala/exercises/simple-cipher/src/test/scala/CipherTest.scala +17 -9
  209. data/tracks/scala/exercises/sublist/src/test/scala/sublist_test.scala +17 -0
  210. data/tracks/scala/exercises/trinary/src/test/scala/TrinaryTest.scala +14 -7
  211. data/tracks/scala/exercises/wordy/src/test/scala/WordProblemTest.scala +28 -14
  212. data/tracks/scala/project/Build.scala +3 -3
  213. data/tracks/scala/testgen/src/main/scala/BowlingTestGenerator.scala +57 -0
  214. data/tracks/sml/config.json +41 -6
  215. data/tracks/sml/exercises/flatten-array/example.sml +6 -0
  216. data/tracks/sml/exercises/flatten-array/test_flatten_array.sml +10 -0
  217. data/tracks/sml/exercises/nth-prime/example.sml +46 -0
  218. data/tracks/sml/exercises/nth-prime/test_nth_prime.sml +14 -0
  219. data/tracks/sml/exercises/raindrops/example.sml +9 -0
  220. data/tracks/sml/exercises/raindrops/raindrops.sml +2 -0
  221. data/tracks/sml/exercises/raindrops/test_raindrops.sml +95 -0
  222. data/tracks/swift/config.json +269 -328
  223. data/tracks/swift/exercises/pangram/PangramExample.swift +17 -0
  224. data/tracks/swift/exercises/pangram/PangramTest.swift +43 -0
  225. data/tracks/swift/xcodeProject/xSwift.xcodeproj/project.pbxproj +16 -0
  226. metadata +95 -3
@@ -0,0 +1,373 @@
1
+ extern crate bowling;
2
+
3
+ use bowling::*;
4
+
5
+ #[test]
6
+ fn roll_returns_a_result() {
7
+ let mut game = BowlingGame::new();
8
+ assert!(game.roll(0).is_ok());
9
+ }
10
+
11
+ #[test]
12
+ #[ignore]
13
+ fn you_can_not_roll_more_than_ten_pins_in_a_single_roll() {
14
+ let mut game = BowlingGame::new();
15
+
16
+ assert!(game.roll(11).is_err());
17
+ }
18
+
19
+ #[test]
20
+ #[ignore]
21
+ fn a_game_score_is_ok_if_ten_frames_have_been_rolled() {
22
+ let mut game = BowlingGame::new();
23
+
24
+ for _ in 0..10 {
25
+ let _ = game.roll(0);
26
+ let _ = game.roll(0);
27
+ }
28
+
29
+ assert!(game.score().is_ok());
30
+ }
31
+
32
+ #[test]
33
+ #[ignore]
34
+ fn you_can_not_score_a_game_with_no_rolls() {
35
+ let game = BowlingGame::new();
36
+
37
+ assert!(game.score().is_err());
38
+ }
39
+
40
+ #[test]
41
+ #[ignore]
42
+ fn a_game_score_is_err_if_fewer_than_ten_frames_have_been_rolled() {
43
+ let mut game = BowlingGame::new();
44
+
45
+ for _ in 0..9 {
46
+ let _ = game.roll(0);
47
+ let _ = game.roll(0);
48
+ }
49
+
50
+ assert!(game.score().is_err());
51
+ }
52
+
53
+ #[test]
54
+ #[ignore]
55
+ fn a_roll_is_err_if_the_game_is_done() {
56
+ let mut game = BowlingGame::new();
57
+
58
+ for _ in 0..10 {
59
+ let _ = game.roll(0);
60
+ let _ = game.roll(0);
61
+ }
62
+
63
+ assert!(game.roll(0).is_err());
64
+ }
65
+
66
+ #[test]
67
+ #[ignore]
68
+ fn twenty_zero_pin_rolls_scores_zero() {
69
+ let mut game = BowlingGame::new();
70
+
71
+ for _ in 0..20 {
72
+ let _ = game.roll(0);
73
+ }
74
+
75
+ assert_eq!(game.score().unwrap(), 0);
76
+ }
77
+
78
+ #[test]
79
+ #[ignore]
80
+ fn ten_frames_without_a_strike_or_spare() {
81
+ let mut game = BowlingGame::new();
82
+
83
+ for _ in 0..10 {
84
+ let _ = game.roll(3);
85
+ let _ = game.roll(6);
86
+ }
87
+
88
+ assert_eq!(game.score().unwrap(), 90);
89
+ }
90
+
91
+ #[test]
92
+ #[ignore]
93
+ fn spare_in_the_first_frame_followed_by_zeros() {
94
+ let mut game = BowlingGame::new();
95
+
96
+ let _ = game.roll(6);
97
+ let _ = game.roll(4);
98
+
99
+ for _ in 0..18 {
100
+ let _ = game.roll(0);
101
+ }
102
+
103
+ assert_eq!(game.score().unwrap(), 10);
104
+ }
105
+
106
+ #[test]
107
+ #[ignore]
108
+ fn points_scored_in_the_roll_after_a_spare_are_counted_twice_as_a_bonus() {
109
+ let mut game = BowlingGame::new();
110
+
111
+ let _ = game.roll(6);
112
+ let _ = game.roll(4);
113
+ let _ = game.roll(3);
114
+
115
+ for _ in 0..17 {
116
+ let _ = game.roll(0);
117
+ }
118
+
119
+ assert_eq!(game.score().unwrap(), 16);
120
+ }
121
+
122
+ #[test]
123
+ #[ignore]
124
+ fn consecutive_spares_each_get_a_one_roll_bonus() {
125
+ let mut game = BowlingGame::new();
126
+
127
+ let _ = game.roll(5);
128
+ let _ = game.roll(5);
129
+ let _ = game.roll(3);
130
+ let _ = game.roll(7);
131
+ let _ = game.roll(4);
132
+
133
+ for _ in 0..15 {
134
+ let _ = game.roll(0);
135
+ }
136
+
137
+ assert_eq!(game.score().unwrap(), 31);
138
+ }
139
+
140
+ #[test]
141
+ #[ignore]
142
+ fn if_the_last_frame_is_a_spare_you_get_one_extra_roll_that_is_scored_once() {
143
+ let mut game = BowlingGame::new();
144
+
145
+ for _ in 0..18 {
146
+ let _ = game.roll(0);
147
+ }
148
+
149
+ let _ = game.roll(5);
150
+ let _ = game.roll(5);
151
+ let _ = game.roll(7);
152
+
153
+ assert_eq!(game.score().unwrap(), 17);
154
+ }
155
+
156
+ #[test]
157
+ #[ignore]
158
+ fn a_strike_earns_ten_points_in_a_frame_with_a_single_roll() {
159
+ let mut game = BowlingGame::new();
160
+
161
+ let _ = game.roll(10);
162
+
163
+ for _ in 0..18 {
164
+ let _ = game.roll(0);
165
+ }
166
+
167
+ assert_eq!(game.score().unwrap(), 10);
168
+ }
169
+
170
+ #[test]
171
+ #[ignore]
172
+ fn points_scored_in_the_two_rolls_after_a_strike_are_counted_twice_as_a_bonus() {
173
+ let mut game = BowlingGame::new();
174
+
175
+ let _ = game.roll(10);
176
+ let _ = game.roll(5);
177
+ let _ = game.roll(3);
178
+
179
+ for _ in 0..16 {
180
+ let _ = game.roll(0);
181
+ }
182
+
183
+ assert_eq!(game.score().unwrap(), 26);
184
+ }
185
+
186
+ #[test]
187
+ #[ignore]
188
+ fn consecutive_strikes_each_get_the_two_roll_bonus() {
189
+ let mut game = BowlingGame::new();
190
+
191
+ let _ = game.roll(10);
192
+ let _ = game.roll(10);
193
+ let _ = game.roll(10);
194
+ let _ = game.roll(5);
195
+ let _ = game.roll(3);
196
+
197
+ for _ in 0..12 {
198
+ let _ = game.roll(0);
199
+ }
200
+
201
+ assert_eq!(game.score().unwrap(), 81);
202
+ }
203
+
204
+ #[test]
205
+ #[ignore]
206
+ fn a_strike_in_the_last_frame_earns_a_two_roll_bonus_that_is_counted_once() {
207
+ let mut game = BowlingGame::new();
208
+
209
+ for _ in 0..18 {
210
+ let _ = game.roll(0);
211
+ }
212
+
213
+ let _ = game.roll(10);
214
+ let _ = game.roll(7);
215
+ let _ = game.roll(1);
216
+
217
+ assert_eq!(game.score().unwrap(), 18);
218
+ }
219
+
220
+ #[test]
221
+ #[ignore]
222
+ fn a_spare_with_the_two_roll_bonus_does_not_get_a_bonus_roll() {
223
+ let mut game = BowlingGame::new();
224
+
225
+ for _ in 0..18 {
226
+ let _ = game.roll(0);
227
+ }
228
+
229
+ let _ = game.roll(10);
230
+ let _ = game.roll(7);
231
+ let _ = game.roll(3);
232
+
233
+ assert_eq!(game.score().unwrap(), 20);
234
+ }
235
+
236
+ #[test]
237
+ #[ignore]
238
+ fn strikes_with_the_two_roll_bonus_do_not_get_a_bonus_roll() {
239
+ let mut game = BowlingGame::new();
240
+
241
+ for _ in 0..18 {
242
+ let _ = game.roll(0);
243
+ }
244
+
245
+ let _ = game.roll(10);
246
+ let _ = game.roll(10);
247
+ let _ = game.roll(10);
248
+
249
+ assert_eq!(game.score().unwrap(), 30);
250
+ }
251
+
252
+ #[test]
253
+ #[ignore]
254
+ fn a_strike_with_the_one_roll_bonus_after_a_spare_in_the_last_frame_does_not_get_a_bonus() {
255
+ let mut game = BowlingGame::new();
256
+
257
+ for _ in 0..18 {
258
+ let _ = game.roll(0);
259
+ }
260
+
261
+ let _ = game.roll(7);
262
+ let _ = game.roll(3);
263
+ let _ = game.roll(10);
264
+
265
+ assert_eq!(game.score().unwrap(), 20);
266
+ }
267
+
268
+ #[test]
269
+ #[ignore]
270
+ fn all_strikes_is_a_perfect_score_of_300() {
271
+ let mut game = BowlingGame::new();
272
+
273
+ for _ in 0..12 {
274
+ let _ = game.roll(10);
275
+ }
276
+
277
+ assert_eq!(game.score().unwrap(), 300);
278
+ }
279
+
280
+ #[test]
281
+ #[ignore]
282
+ fn you_can_not_roll_more_than_ten_pins_in_a_single_frame() {
283
+ let mut game = BowlingGame::new();
284
+
285
+ assert!(game.roll(5).is_ok());
286
+ assert!(game.roll(6).is_err());
287
+ }
288
+
289
+ #[test]
290
+ #[ignore]
291
+ fn the_two_balls_after_a_final_strike_can_not_score_an_invalid_number_of_pins() {
292
+ let mut game = BowlingGame::new();
293
+
294
+ for _ in 0..18 {
295
+ let _ = game.roll(0);
296
+ }
297
+
298
+ let _ = game.roll(10);
299
+
300
+ assert!(game.roll(5).is_ok());
301
+ assert!(game.roll(6).is_err());
302
+ }
303
+
304
+ #[test]
305
+ #[ignore]
306
+ fn the_two_balls_after_a_final_strike_can_be_a_strike_and_non_strike() {
307
+ let mut game = BowlingGame::new();
308
+
309
+ for _ in 0..18 {
310
+ let _ = game.roll(0);
311
+ }
312
+
313
+ let _ = game.roll(10);
314
+
315
+ assert!(game.roll(10).is_ok());
316
+ assert!(game.roll(6).is_ok());
317
+ }
318
+
319
+ #[test]
320
+ #[ignore]
321
+ fn the_two_balls_after_a_final_strike_can_not_be_a_non_strike_followed_by_a_strike() {
322
+ let mut game = BowlingGame::new();
323
+
324
+ for _ in 0..18 {
325
+ let _ = game.roll(0);
326
+ }
327
+
328
+ let _ = game.roll(10);
329
+
330
+ assert!(game.roll(6).is_ok());
331
+ assert!(game.roll(10).is_err());
332
+ }
333
+
334
+ #[test]
335
+ #[ignore]
336
+ fn if_the_last_frame_is_a_strike_you_can_not_score_before_the_extra_rolls_are_taken() {
337
+ let mut game = BowlingGame::new();
338
+
339
+ for _ in 0..18 {
340
+ let _ = game.roll(0);
341
+ }
342
+
343
+ let _ = game.roll(10);
344
+
345
+ assert!(game.score().is_err());
346
+
347
+ let _ = game.roll(10);
348
+
349
+ assert!(game.score().is_err());
350
+
351
+ let _ = game.roll(10);
352
+
353
+ assert!(game.score().is_ok());
354
+ }
355
+
356
+ #[test]
357
+ #[ignore]
358
+ fn if_the_last_frame_is_a_spare_you_can_not_create_a_score_before_extra_roll_is_taken() {
359
+ let mut game = BowlingGame::new();
360
+
361
+ for _ in 0..18 {
362
+ let _ = game.roll(0);
363
+ }
364
+
365
+ let _ = game.roll(5);
366
+ let _ = game.roll(5);
367
+
368
+ assert!(game.score().is_err());
369
+
370
+ let _ = game.roll(10);
371
+
372
+ assert!(game.score().is_ok());
373
+ }
@@ -0,0 +1,7 @@
1
+ # Generated by Cargo
2
+ # will have compiled files and executables
3
+ /target/
4
+
5
+ # Remove Cargo.lock from gitignore if creating an executable, leave it for libraries
6
+ # More information here http://doc.crates.io/guide.html#cargotoml-vs-cargolock
7
+ Cargo.lock
@@ -0,0 +1,3 @@
1
+ [package]
2
+ name = "grains"
3
+ version = "0.0.0"
@@ -0,0 +1,11 @@
1
+ pub fn square(s: u32) -> u64 {
2
+ if s == 0 || s > 64 {
3
+ panic!("Square must be between 1 and 64");
4
+ }
5
+
6
+ 2u64.pow(s - 1)
7
+ }
8
+
9
+ pub fn total() -> u64 {
10
+ (1..65).fold(0, |acc, s| acc + square(s))
11
+ }
@@ -0,0 +1,7 @@
1
+ pub fn square(s: u32) -> u64 {
2
+ unimplemented!();
3
+ }
4
+
5
+ pub fn total() -> u64 {
6
+ unimplemented!();
7
+ }
@@ -0,0 +1,63 @@
1
+ extern crate grains;
2
+
3
+ #[test]
4
+ fn square_one() {
5
+ assert_eq!(grains::square(1), 1);
6
+ }
7
+
8
+ #[test]
9
+ #[ignore]
10
+ fn square_two() {
11
+ assert_eq!(grains::square(2), 2);
12
+ }
13
+
14
+ #[test]
15
+ #[ignore]
16
+ fn square_three() {
17
+ assert_eq!(grains::square(3), 4);
18
+ }
19
+
20
+ #[test]
21
+ #[ignore]
22
+ fn square_four() {
23
+ assert_eq!(grains::square(4), 8);
24
+ }
25
+
26
+ #[test]
27
+ #[ignore]
28
+ fn square_sixteen() {
29
+ assert_eq!(grains::square(16), 32_768);
30
+ }
31
+
32
+ #[test]
33
+ #[ignore]
34
+ fn square_thirty_two() {
35
+ assert_eq!(grains::square(32), 2_147_483_648);
36
+ }
37
+
38
+ #[test]
39
+ #[ignore]
40
+ fn square_sixty_four() {
41
+ assert_eq!(grains::square(64), 9_223_372_036_854_775_808);
42
+ }
43
+
44
+ #[test]
45
+ #[ignore]
46
+ #[should_panic(expected = "Square must be between 1 and 64")]
47
+ fn square_zero_panics() {
48
+ grains::square(0);
49
+ }
50
+
51
+ #[test]
52
+ #[ignore]
53
+ #[should_panic(expected = "Square must be between 1 and 64")]
54
+ fn square_sixty_five_panics() {
55
+ grains::square(65);
56
+ }
57
+
58
+ #[test]
59
+ #[ignore]
60
+ fn total_sums_all_squares() {
61
+ assert_eq!(grains::total(), 18_446_744_073_709_551_615);
62
+ grains::total();
63
+ }
@@ -23,6 +23,7 @@ raindrops | case (or `format`). Mutable string
23
23
  bob | chars, string functions
24
24
  beer-song | case, string concatenation, vector (optional), loop
25
25
  difference-of-squares | fold & map
26
+ grains | math, panic
26
27
 
27
28
  ## Getting Rusty
28
29
 
@@ -48,6 +49,7 @@ grade-school | struct, entry api, Vec, Option
48
49
  robot-simulator | Immutability, enum
49
50
  bracket-push | From trait, stack or recursion
50
51
  queen-attack | struct, trait (optional), Result
52
+ bowling | struct, Result, goofy bowling logic
51
53
  sublist | enum, generic over type
52
54
  space-age | Custom Trait, From Trait, Default Trait implementation
53
55
  allergies | struct, enum, bitwise (probably), vectors, filter
@@ -6,6 +6,44 @@ Exercism Exercises in Scala
6
6
 
7
7
  Please see the [contributing guide](https://github.com/exercism/x-api/blob/master/CONTRIBUTING.md#the-exercise-data)
8
8
 
9
+ ### Generated Test Suites
10
+
11
+ Some of the test suites have been generated from shared test data. If a test suite was
12
+ generated from test data, then the test suite should not be modified by hand. Instead
13
+ the shared test data should be modified, and the generator rerun. To determine if
14
+ a test suite generator was used, look inside the `testgen/src/main/scala` directory. The test
15
+ suite generators are named in the form `ProblemNameTestGenerator.scala`. Where
16
+ `ProblemName` is a close match for the Exercism problem name.
17
+
18
+ [the shared problem metadata](https://github.com/exercism/x-common).
19
+
20
+ For example, take a look at the `all-your-base/canonical-data.json` file in the x-common repository, as well
21
+ as the following files in the xscala repository:
22
+
23
+ 1. `testgen/src/main/scala/AllYourBaseTestGenerator.scala` - test suite generator for all-your-base
24
+ 1. `exercises/all-your-base/src/test/scala/AllYourBase.scala`- generated test suite
25
+
26
+ Since a generator was used, the`exercises/all-your-base/src/test/scala/AllYourBase.scala` will never be edited directly.
27
+ If there's a missing test case, then additional inputs/outputs should be submitted to the x-common repository.
28
+
29
+ Note that the the test suite generators do not format the test suite source code. The generated test suite should be
30
+ formatted before being submitted.
31
+
32
+ When submitting new exercises we encourage that a test suite generator and generated test suite is
33
+ included.
34
+
35
+ ## Pull Requests
36
+
37
+ We welcome pull requests that provide fixes to existing test suites (missing
38
+ tests, interesting edge cases, improved APIs), as well as new problems.
39
+
40
+ If you're unsure, then go ahead and open a GitHub issue, and we'll discuss the
41
+ change.
42
+
43
+ Please submit changes to a single problem per pull request unless you're
44
+ submitting a general change across many of the problems (e.g. formatting).
45
+
46
+
9
47
  ## License
10
48
 
11
49
  The MIT License (MIT)
@@ -3,75 +3,6 @@
3
3
  "language": "Scala",
4
4
  "repository": "https://github.com/exercism/xscala",
5
5
  "active": true,
6
- "problems": [
7
- "hello-world",
8
- "bob",
9
- "sum-of-multiples",
10
- "hamming",
11
- "word-count",
12
- "pangram",
13
- "anagram",
14
- "nucleotide-count",
15
- "phone-number",
16
- "grade-school",
17
- "robot-name",
18
- "leap",
19
- "etl",
20
- "meetup",
21
- "space-age",
22
- "grains",
23
- "gigasecond",
24
- "scrabble-score",
25
- "difference-of-squares",
26
- "accumulate",
27
- "sublist",
28
- "rna-transcription",
29
- "triangle",
30
- "roman-numerals",
31
- "prime-factors",
32
- "raindrops",
33
- "allergies",
34
- "atbash-cipher",
35
- "all-your-base",
36
- "bank-account",
37
- "crypto-square",
38
- "kindergarten-garden",
39
- "robot-simulator",
40
- "bracket-push",
41
- "queen-attack",
42
- "binary-search-tree",
43
- "largest-series-product",
44
- "luhn",
45
- "clock",
46
- "matrix",
47
- "house",
48
- "zebra-puzzle",
49
- "minesweeper",
50
- "ocr-numbers",
51
- "wordy",
52
- "food-chain",
53
- "linked-list",
54
- "custom-set",
55
- "nth-prime",
56
- "palindrome-products",
57
- "pascals-triangle",
58
- "pig-latin",
59
- "pythagorean-triplet",
60
- "saddle-points",
61
- "say",
62
- "secret-handshake",
63
- "series",
64
- "sieve",
65
- "simple-cipher",
66
- "change",
67
- "connect",
68
- "parallel-letter-frequency",
69
- "sgf-parsing",
70
- "acronym",
71
- "zipper",
72
- "forth",
73
- "lens-person"
74
- ],
75
6
  "exercises": [
76
7
  {
77
8
  "slug": "hello-world",
@@ -84,16 +15,16 @@
84
15
  "slug": "bob",
85
16
  "difficulty": 1,
86
17
  "topics": [
87
- "Strings",
18
+ "Strings",
88
19
  "Control-flow (if-else statements)",
89
- "Pattern matching"
20
+ "Pattern matching"
90
21
  ]
91
22
  },
92
23
  {
93
24
  "slug": "sum-of-multiples",
94
25
  "difficulty": 1,
95
26
  "topics": [
96
- "Filtering"
27
+ "Filtering"
97
28
  ]
98
29
  },
99
30
  {
@@ -102,7 +33,7 @@
102
33
  "topics": [
103
34
  "Strings",
104
35
  "Filtering",
105
- "Optional values"
36
+ "Optional values"
106
37
  ]
107
38
  },
108
39
  {
@@ -411,6 +342,12 @@
411
342
  "topics": [
412
343
  ]
413
344
  },
345
+ {
346
+ "slug": "alphametics",
347
+ "difficulty": 1,
348
+ "topics": [
349
+ ]
350
+ },
414
351
  {
415
352
  "slug": "secret-handshake",
416
353
  "difficulty": 1,
@@ -482,7 +419,16 @@
482
419
  "difficulty": 1,
483
420
  "topics": [
484
421
  ]
485
- }
422
+ },
423
+ {
424
+ "slug": "bowling",
425
+ "difficulty": 6,
426
+ "topics": [
427
+ "Algorithms",
428
+ "Control-flow (if-else statements)",
429
+ "Lists"
430
+ ]
431
+ }
486
432
  ],
487
433
  "deprecated": [
488
434
  "binary",
@@ -9,24 +9,28 @@ class AccumulateTest extends FlatSpec with Matchers {
9
9
  }
10
10
 
11
11
  it should "accumulate squares" in {
12
+ pending
12
13
  val accumulate = new Accumulate
13
14
  val accumulation = accumulate.accumulate[Int, Int](x => x * x, List(1, 2, 3))
14
15
  accumulation should be (List(1, 4, 9))
15
16
  }
16
17
 
17
18
  it should "accumulate upcases" in {
19
+ pending
18
20
  val accumulate = new Accumulate
19
21
  val accumulation = accumulate.accumulate[String, String](_.map(_.toUpper), List("hello", "world"))
20
22
  accumulation should be (List("HELLO", "WORLD"))
21
23
  }
22
24
 
23
25
  it should "accumulate reversed strings" in {
26
+ pending
24
27
  val accumulate = new Accumulate
25
28
  val accumulation = accumulate.accumulate[String, String](_.reverse, List("eht", "kciuq", "nworb", "xof", "cte"))
26
29
  accumulation should be (List("the", "quick", "brown", "fox", "etc"))
27
30
  }
28
31
 
29
32
  it should "allow different return type" in {
33
+ pending
30
34
  val accumulate = new Accumulate
31
35
  val accumulation = accumulate.accumulate[Int, String](_.toString, List(1, 2, 3))
32
36
  accumulation should be (List("1", "2", "3"))