trackler 2.2.1.100 → 2.2.1.101

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 (204) hide show
  1. checksums.yaml +4 -4
  2. data/lib/trackler/version.rb +1 -1
  3. data/problem-specifications/exercises/kindergarten-garden/canonical-data.json +37 -19
  4. data/problem-specifications/exercises/ocr-numbers/canonical-data.json +144 -110
  5. data/problem-specifications/exercises/palindrome-products/canonical-data.json +49 -25
  6. data/problem-specifications/exercises/poker/canonical-data.json +171 -115
  7. data/problem-specifications/exercises/prime-factors/canonical-data.json +22 -8
  8. data/problem-specifications/exercises/protein-translation/canonical-data.json +70 -24
  9. data/problem-specifications/exercises/proverb/canonical-data.json +24 -12
  10. data/problem-specifications/exercises/queen-attack/canonical-data.json +115 -91
  11. data/problem-specifications/exercises/rail-fence-cipher/canonical-data.json +25 -13
  12. data/problem-specifications/exercises/raindrops/canonical-data.json +55 -19
  13. data/problem-specifications/exercises/rational-numbers/canonical-data.json +374 -0
  14. data/problem-specifications/exercises/rational-numbers/description.md +27 -0
  15. data/problem-specifications/exercises/rational-numbers/metadata.yml +4 -0
  16. data/problem-specifications/exercises/rectangles/canonical-data.json +93 -67
  17. data/problem-specifications/exercises/reverse-string/canonical-data.json +16 -6
  18. data/problem-specifications/exercises/rna-transcription/metadata.yml +3 -3
  19. data/problem-specifications/exercises/roman-numerals/canonical-data.json +10 -2
  20. data/tracks/bash/config.json +11 -11
  21. data/tracks/c/exercises/roman-numerals/test/test_roman_numerals.c +7 -0
  22. data/tracks/clojure/exercises/armstrong-numbers/README.md +1 -1
  23. data/tracks/delphi/config.json +11 -0
  24. data/tracks/delphi/exercises/clock/uClockExample.pas +6 -1
  25. data/tracks/delphi/exercises/clock/uClockTest.pas +22 -19
  26. data/tracks/delphi/exercises/isbn-verifier/README.md +1 -1
  27. data/tracks/delphi/exercises/reverse-string/README.md +1 -1
  28. data/tracks/delphi/exercises/rna-transcription/README.md +1 -1
  29. data/tracks/delphi/exercises/roman-numerals/uRomanNumeralsTest.pas +14 -0
  30. data/tracks/delphi/exercises/space-age/README.md +45 -0
  31. data/tracks/delphi/exercises/space-age/SpaceAge.dpr +60 -0
  32. data/tracks/delphi/exercises/space-age/uSpaceAgeExample.pas +120 -0
  33. data/tracks/delphi/exercises/space-age/uSpaceAgeTests.pas +135 -0
  34. data/tracks/delphi/exercises/two-fer/README.md +1 -1
  35. data/tracks/elixir/exercises/nth-prime/nth_prime.exs +0 -1
  36. data/tracks/fsharp/exercises/pov/PovTest.fs +66 -53
  37. data/tracks/fsharp/exercises/space-age/Example.fs +11 -11
  38. data/tracks/fsharp/exercises/space-age/SpaceAge.fs +1 -1
  39. data/tracks/fsharp/exercises/space-age/SpaceAgeTest.fs +21 -34
  40. data/tracks/fsharp/exercises/triangle/Example.fs +11 -16
  41. data/tracks/fsharp/exercises/triangle/Triangle.fs +4 -5
  42. data/tracks/fsharp/exercises/triangle/TriangleTest.fs +44 -31
  43. data/tracks/fsharp/generators/Generators.fs +121 -0
  44. data/tracks/go/config.json +12 -0
  45. data/tracks/go/exercises/clock/.meta/gen.go +37 -13
  46. data/tracks/go/exercises/clock/cases_test.go +10 -10
  47. data/tracks/go/exercises/clock/clock_test.go +16 -2
  48. data/tracks/go/exercises/clock/example.go +4 -0
  49. data/tracks/go/exercises/clock/example_clock_test.go +3 -3
  50. data/tracks/go/exercises/parallel-letter-frequency/.meta/hints.md +33 -0
  51. data/tracks/go/exercises/parallel-letter-frequency/README.md +35 -0
  52. data/tracks/go/exercises/raindrops/.meta/hints.md +7 -4
  53. data/tracks/go/exercises/raindrops/README.md +12 -0
  54. data/tracks/go/exercises/roman-numerals/.meta/gen.go +4 -2
  55. data/tracks/go/exercises/roman-numerals/cases_test.go +3 -2
  56. data/tracks/go/exercises/space-age/.meta/hints.md +10 -0
  57. data/tracks/go/exercises/space-age/README.md +14 -1
  58. data/tracks/go/exercises/twelve-days/README.md +2 -5
  59. data/tracks/go/exercises/two-bucket/.meta/gen.go +62 -0
  60. data/tracks/go/exercises/two-bucket/.meta/hints.md +16 -0
  61. data/tracks/go/exercises/two-bucket/README.md +72 -0
  62. data/tracks/go/exercises/two-bucket/cases_test.go +44 -0
  63. data/tracks/go/exercises/two-bucket/example.go +198 -0
  64. data/tracks/go/exercises/two-bucket/two_bucket_test.go +61 -0
  65. data/tracks/idris/.travis.yml +3 -2
  66. data/tracks/idris/bin/fetch-idris-testing.sh +11 -0
  67. data/tracks/idris/bin/solve_exercises.sh +2 -2
  68. data/tracks/idris/config.json +11 -0
  69. data/tracks/idris/config/exercise_readme.go.tmpl +0 -3
  70. data/tracks/idris/docs/INSTALLATION.md +22 -0
  71. data/tracks/idris/docs/TESTS.md +12 -4
  72. data/tracks/idris/exercises/accumulate/src/Accumulate.idr +5 -0
  73. data/tracks/idris/exercises/hamming/Hamming.ipkg +2 -0
  74. data/tracks/idris/exercises/hamming/src/{example.idr → Example.idr} +5 -1
  75. data/tracks/idris/exercises/hamming/src/Hamming.idr +13 -5
  76. data/tracks/idris/exercises/hamming/src/Test/Hamming.idr +31 -58
  77. data/tracks/idris/exercises/hello-world/HelloWorld.ipkg +2 -0
  78. data/tracks/idris/exercises/hello-world/src/Example.idr +9 -0
  79. data/tracks/idris/exercises/hello-world/src/HelloWorld.idr +6 -1
  80. data/tracks/idris/exercises/hello-world/src/Test/HelloWorld.idr +18 -18
  81. data/tracks/idris/exercises/leap/Leap.ipkg +2 -0
  82. data/tracks/idris/exercises/leap/src/{example.idr → Example.idr} +4 -0
  83. data/tracks/idris/exercises/leap/src/Leap.idr +5 -1
  84. data/tracks/idris/exercises/leap/src/Test/Leap.idr +21 -30
  85. data/tracks/idris/exercises/rna-transcription/Makefile +23 -0
  86. data/tracks/idris/exercises/rna-transcription/README.md +27 -0
  87. data/tracks/idris/exercises/rna-transcription/RnaTranscription.ipkg +5 -0
  88. data/tracks/idris/exercises/rna-transcription/src/RnaTranscription.idr +17 -0
  89. data/tracks/idris/exercises/rna-transcription/src/Test/RnaTranscription.idr +27 -0
  90. data/tracks/idris/exercises/rna-transcription/src/example.idr +35 -0
  91. data/tracks/java/exercises/etl/.meta/version +1 -0
  92. data/tracks/java/exercises/gigasecond/.meta/version +1 -0
  93. data/tracks/java/exercises/isbn-verifier/README.md +1 -1
  94. data/tracks/java/exercises/nucleotide-count/.meta/src/reference/java/NucleotideCounter.java +7 -1
  95. data/tracks/java/exercises/nucleotide-count/.meta/version +1 -0
  96. data/tracks/java/exercises/nucleotide-count/src/test/java/NucleotideCounterTest.java +19 -54
  97. data/tracks/java/exercises/proverb/.meta/version +1 -0
  98. data/tracks/java/exercises/reverse-string/README.md +1 -1
  99. data/tracks/java/exercises/rna-transcription/README.md +1 -1
  100. data/tracks/java/exercises/sum-of-multiples/.meta/version +1 -0
  101. data/tracks/java/exercises/sum-of-multiples/src/test/java/SumOfMultiplesTest.java +13 -1
  102. data/tracks/kotlin/config/exercise_readme.go.tmpl +0 -3
  103. data/tracks/kotlin/docs/TESTS.md +1 -1
  104. data/tracks/objective-c/config.json +11 -0
  105. data/tracks/objective-c/exercises/collatz-conjecture/CollatzConjectureExample.h +7 -0
  106. data/tracks/objective-c/exercises/collatz-conjecture/CollatzConjectureExample.m +26 -0
  107. data/tracks/objective-c/exercises/collatz-conjecture/CollatzConjectureTest.m +39 -0
  108. data/tracks/objective-c/xcodeProject/ObjectiveC.xcodeproj/project.pbxproj +31 -1
  109. data/tracks/objective-c/xcodeProject/ObjectiveC.xcodeproj/xcshareddata/xcschemes/OCLint.xcscheme +3 -1
  110. data/tracks/objective-c/xcodeProject/ObjectiveC.xcodeproj/xcshareddata/xcschemes/xobjectivecTest.xcscheme +3 -1
  111. data/tracks/ocaml/exercises/forth/example.ml +9 -9
  112. data/tracks/ocaml/tools/test-generator/Makefile +3 -9
  113. data/tracks/ocaml/tools/test-generator/src/test_gen.ml +18 -16
  114. data/tracks/perl6/exercises/acronym/.meta/exercise-data.yaml +1 -1
  115. data/tracks/perl6/exercises/acronym/acronym.t +4 -14
  116. data/tracks/perl6/exercises/all-your-base/all-your-base.t +0 -2
  117. data/tracks/perl6/exercises/allergies/allergies.t +0 -2
  118. data/tracks/perl6/exercises/anagram/.meta/exercise-data.yaml +1 -1
  119. data/tracks/perl6/exercises/anagram/anagram.t +2 -40
  120. data/tracks/perl6/exercises/atbash-cipher/atbash-cipher.t +0 -1
  121. data/tracks/perl6/exercises/bob/bob.t +0 -2
  122. data/tracks/perl6/exercises/clock/.meta/exercise-data.yaml +15 -11
  123. data/tracks/perl6/exercises/clock/.meta/solutions/Clock.pm6 +5 -1
  124. data/tracks/perl6/exercises/clock/Clock.pm6 +1 -1
  125. data/tracks/perl6/exercises/clock/clock.t +314 -217
  126. data/tracks/perl6/exercises/etl/etl.t +0 -2
  127. data/tracks/perl6/exercises/flatten-array/flatten-array.t +0 -2
  128. data/tracks/perl6/exercises/grains/grains.t +0 -2
  129. data/tracks/perl6/exercises/hamming/.meta/exercise-data.yaml +2 -2
  130. data/tracks/perl6/exercises/hamming/hamming.t +63 -35
  131. data/tracks/perl6/exercises/hello-world/hello-world.t +2 -3
  132. data/tracks/perl6/exercises/leap/.meta/exercise-data.yaml +1 -1
  133. data/tracks/perl6/exercises/leap/leap.t +14 -8
  134. data/tracks/perl6/exercises/luhn/luhn.t +0 -2
  135. data/tracks/perl6/exercises/nucleotide-count/.meta/exercise-data.yaml +2 -2
  136. data/tracks/perl6/exercises/nucleotide-count/nucleotide-count.t +18 -10
  137. data/tracks/perl6/exercises/pangram/.meta/exercise-data.yaml +1 -1
  138. data/tracks/perl6/exercises/pangram/pangram.t +32 -14
  139. data/tracks/perl6/exercises/phone-number/.meta/exercise-data.yaml +4 -4
  140. data/tracks/perl6/exercises/phone-number/.meta/solutions/Phone.pm6 +1 -1
  141. data/tracks/perl6/exercises/phone-number/Phone.pm6 +1 -1
  142. data/tracks/perl6/exercises/phone-number/phone-number.t +59 -21
  143. data/tracks/perl6/exercises/raindrops/raindrops.t +0 -2
  144. data/tracks/perl6/exercises/rna-transcription/.meta/exercise-data.yaml +1 -1
  145. data/tracks/perl6/exercises/rna-transcription/README.md +1 -1
  146. data/tracks/perl6/exercises/rna-transcription/rna-transcription.t +17 -9
  147. data/tracks/perl6/exercises/roman-numerals/.meta/exercise-data.yaml +3 -3
  148. data/tracks/perl6/exercises/roman-numerals/.meta/solutions/RomanNumerals.pm6 +1 -1
  149. data/tracks/perl6/exercises/roman-numerals/RomanNumerals.pm6 +1 -1
  150. data/tracks/perl6/exercises/roman-numerals/roman-numerals.t +66 -24
  151. data/tracks/perl6/exercises/scrabble-score/.meta/exercise-data.yaml +1 -1
  152. data/tracks/perl6/exercises/scrabble-score/scrabble-score.t +35 -15
  153. data/tracks/perl6/exercises/space-age/.meta/exercise-data.yaml +1 -1
  154. data/tracks/perl6/exercises/space-age/space-age.t +34 -20
  155. data/tracks/perl6/exercises/two-fer/.meta/exercise-data.yaml +2 -2
  156. data/tracks/perl6/exercises/two-fer/two-fer.t +15 -11
  157. data/tracks/perl6/exercises/word-count/.meta/exercise-data.yaml +1 -1
  158. data/tracks/perl6/exercises/word-count/word-count.t +46 -26
  159. data/tracks/perl6/exercises/wordy/.meta/exercise-data.yaml +2 -2
  160. data/tracks/perl6/exercises/wordy/wordy.t +51 -21
  161. data/tracks/perl6/lib/Exercism/Generator.pm6 +1 -1
  162. data/tracks/perl6/t/generated-tests.t +1 -1
  163. data/tracks/perl6/templates/test.mustache +0 -1
  164. data/tracks/python/config.json +12 -0
  165. data/tracks/python/exercises/forth/example.py +1 -1
  166. data/tracks/python/exercises/forth/forth_test.py +43 -38
  167. data/tracks/python/exercises/spiral-matrix/README.md +42 -0
  168. data/tracks/python/exercises/spiral-matrix/example.py +11 -0
  169. data/tracks/python/exercises/spiral-matrix/spiral_matrix.py +2 -0
  170. data/tracks/python/exercises/spiral-matrix/spiral_matrix_test.py +40 -0
  171. data/tracks/racket/config/exercise_readme.go.tmpl +24 -4
  172. data/tracks/racket/exercises/accumulate/README.md +3 -6
  173. data/tracks/racket/exercises/acronym/README.md +3 -4
  174. data/tracks/racket/exercises/allergies/README.md +3 -4
  175. data/tracks/racket/exercises/anagram/README.md +3 -3
  176. data/tracks/racket/exercises/bob/README.md +5 -3
  177. data/tracks/racket/exercises/collatz-conjecture/README.md +3 -3
  178. data/tracks/racket/exercises/difference-of-squares/README.md +3 -3
  179. data/tracks/racket/exercises/etl/README.md +6 -4
  180. data/tracks/racket/exercises/gigasecond/README.md +3 -3
  181. data/tracks/racket/exercises/grains/README.md +3 -4
  182. data/tracks/racket/exercises/grep/README.md +15 -15
  183. data/tracks/racket/exercises/hamming/README.md +3 -3
  184. data/tracks/racket/exercises/hello-world/README.md +1 -1
  185. data/tracks/racket/exercises/leap/README.md +4 -4
  186. data/tracks/racket/exercises/list-ops/README.md +3 -4
  187. data/tracks/racket/exercises/meetup/README.md +19 -15
  188. data/tracks/racket/exercises/nucleotide-count/README.md +11 -25
  189. data/tracks/racket/exercises/perfect-numbers/README.md +5 -5
  190. data/tracks/racket/exercises/phone-number/README.md +7 -6
  191. data/tracks/racket/exercises/raindrops/README.md +3 -3
  192. data/tracks/racket/exercises/rna-transcription/README.md +4 -4
  193. data/tracks/racket/exercises/roman-numerals/README.md +4 -4
  194. data/tracks/racket/exercises/say/README.md +3 -3
  195. data/tracks/racket/exercises/scrabble-score/README.md +6 -4
  196. data/tracks/racket/exercises/word-count/README.md +4 -5
  197. data/tracks/scheme/config/exercise_readme.go.tmpl +0 -3
  198. data/tracks/scheme/docs/INSTALLATION.md +23 -14
  199. metadata +40 -9
  200. data/tracks/idris/docs/EXERCISE_README_INSERT.md +0 -0
  201. data/tracks/idris/exercises/hello-world/src/example.idr +0 -5
  202. data/tracks/kotlin/config/exercise-readme-insert.md +0 -1
  203. data/tracks/racket/docs/EXERCISE_README_INSERT.md +0 -23
  204. data/tracks/scheme/docs/EXERCISE_README_INSERT.md +0 -0
@@ -34,7 +34,7 @@ For example, if you're submitting `ubob.pas` for the Bob exercise, the submit co
34
34
 
35
35
  ## Source
36
36
 
37
- This is an exercise to introduce users to basic programming constructs, just after hello World. [https://en.wikipedia.org/wiki/Two-fer](https://en.wikipedia.org/wiki/Two-fer)
37
+ This is an exercise to introduce users to basic programming constructs, just after Hello World. [https://en.wikipedia.org/wiki/Two-fer](https://en.wikipedia.org/wiki/Two-fer)
38
38
 
39
39
  ## Submitting Incomplete Solutions
40
40
  It's possible to submit an incomplete solution so you can see how others have completed the exercise.
@@ -6,5 +6,4 @@ defmodule Prime do
6
6
  @spec nth(non_neg_integer) :: non_neg_integer
7
7
  def nth(count) do
8
8
  end
9
-
10
9
  end
@@ -1,80 +1,93 @@
1
- // This file was created manually and its version is 1.0.0.
1
+ // This file was auto-generated based on version 1.1.1 of the canonical data.
2
2
 
3
3
  module PovTest
4
4
 
5
- open Xunit
6
5
  open FsUnit.Xunit
6
+ open Xunit
7
7
 
8
8
  open Pov
9
9
 
10
- let x = "x"
11
- let leaf v = mkGraph v []
12
-
13
- let singleton = mkGraph x []
14
- let flat = mkGraph "root" (List.map leaf ["a"; "b"; x; "c"])
15
- let nested = mkGraph "level-0" [mkGraph "level-1" [mkGraph "level-2" [mkGraph "level-3" [mkGraph x []]]]]
16
- let kids = mkGraph "root" [mkGraph x [mkGraph "kid-0" []; mkGraph "kid-1" []]]
17
- let cousins = mkGraph "grandparent" [
18
- mkGraph "parent" [
19
- mkGraph x [leaf "kid-a"; leaf "kid-b"];
20
- (leaf "sibling-0");
21
- (leaf "sibling-1")];
22
- mkGraph "uncle" [
23
- (leaf "cousin-0");
24
- (leaf "cousin-1")]]
25
-
26
- let singleton' = singleton
27
- let flat' = mkGraph x [mkGraph "root" (List.map leaf ["a"; "b"; "c"])]
28
- let nested' = mkGraph x [mkGraph "level-3" [mkGraph "level-2" [mkGraph "level-1" [mkGraph "level-0" []]]]]
29
- let kids' = mkGraph x [mkGraph "kid-0" []; mkGraph "kid-1" []; mkGraph "root" []]
30
- let cousins' = mkGraph x [
31
- leaf "kid-a";
32
- leaf "kid-b";
33
- mkGraph "parent" [
34
- mkGraph "sibling-0" [];
35
- mkGraph "sibling-1" [];
36
- mkGraph "grandparent" [
37
- mkGraph "uncle" [
38
- mkGraph "cousin-0" [];
39
- mkGraph "cousin-1" []]]]]
10
+ let rec graphToList graph =
11
+ let right =
12
+ graph.children
13
+ |> List.sortBy (fun x -> x.value)
14
+ |> List.collect graphToList
15
+ [graph.value] @ right
16
+ let mapToList graph = match graph with | Some x -> graphToList x | None -> []
40
17
 
41
18
  [<Fact>]
42
- let ``Reparent singleton`` () =
43
- fromPOV x singleton |> should equal <| Some singleton'
19
+ let ``Results in the same tree if the input tree is a singleton`` () =
20
+ let tree = mkGraph "x" []
21
+ let expected = mkGraph "x" []
22
+ fromPOV "x" tree |> mapToList |> should equal <| graphToList expected
23
+
24
+ [<Fact(Skip = "Remove to run test")>]
25
+ let ``Can reroot a tree with a parent and one sibling`` () =
26
+ let tree = mkGraph "parent" [mkGraph "x" []; mkGraph "sibling" []]
27
+ let expected = mkGraph "x" [mkGraph "parent" [mkGraph "sibling" []]]
28
+ fromPOV "x" tree |> mapToList |> should equal <| graphToList expected
29
+
30
+ [<Fact(Skip = "Remove to run test")>]
31
+ let ``Can reroot a tree with a parent and many siblings`` () =
32
+ let tree = mkGraph "parent" [mkGraph "a" []; mkGraph "x" []; mkGraph "b" []; mkGraph "c" []]
33
+ let expected = mkGraph "x" [mkGraph "parent" [mkGraph "a" []; mkGraph "b" []; mkGraph "c" []]]
34
+ fromPOV "x" tree |> mapToList |> should equal <| graphToList expected
44
35
 
45
36
  [<Fact(Skip = "Remove to run test")>]
46
- let ``Reparent flat`` () =
47
- fromPOV x flat |> should equal <| Some flat'
37
+ let ``Can reroot a tree with new root deeply nested in tree`` () =
38
+ let tree = mkGraph "level-0" [mkGraph "level-1" [mkGraph "level-2" [mkGraph "level-3" [mkGraph "x" []]]]]
39
+ let expected = mkGraph "x" [mkGraph "level-3" [mkGraph "level-2" [mkGraph "level-1" [mkGraph "level-0" []]]]]
40
+ fromPOV "x" tree |> mapToList |> should equal <| graphToList expected
48
41
 
49
42
  [<Fact(Skip = "Remove to run test")>]
50
- let ``Reparent nested`` () =
51
- fromPOV x nested |> should equal <| Some nested'
43
+ let ``Moves children of the new root to same level as former parent`` () =
44
+ let tree = mkGraph "parent" [mkGraph "x" [mkGraph "kid-0" []; mkGraph "kid-1" []]]
45
+ let expected = mkGraph "x" [mkGraph "kid-0" []; mkGraph "kid-1" []; mkGraph "parent" []]
46
+ fromPOV "x" tree |> mapToList |> should equal <| graphToList expected
52
47
 
53
48
  [<Fact(Skip = "Remove to run test")>]
54
- let ``Reparent kids`` () =
55
- fromPOV x kids |> should equal <| Some kids'
49
+ let ``Can reroot a complex tree with cousins`` () =
50
+ let tree = mkGraph "grandparent" [mkGraph "parent" [mkGraph "x" [mkGraph "kid-0" []; mkGraph "kid-1" []]; mkGraph "sibling-0" []; mkGraph "sibling-1" []]; mkGraph "uncle" [mkGraph "cousin-0" []; mkGraph "cousin-1" []]]
51
+ let expected = mkGraph "x" [mkGraph "kid-1" []; mkGraph "kid-0" []; mkGraph "parent" [mkGraph "sibling-0" []; mkGraph "sibling-1" []; mkGraph "grandparent" [mkGraph "uncle" [mkGraph "cousin-0" []; mkGraph "cousin-1" []]]]]
52
+ fromPOV "x" tree |> mapToList |> should equal <| graphToList expected
56
53
 
57
54
  [<Fact(Skip = "Remove to run test")>]
58
- let ``Reparent cousins`` () =
59
- fromPOV x cousins |> should equal <| Some cousins'
55
+ let ``Errors if target does not exist in a singleton tree`` () =
56
+ let tree = mkGraph "x" []
57
+ fromPOV "nonexistent" tree |> should equal None
60
58
 
61
59
  [<Fact(Skip = "Remove to run test")>]
62
- let ``Reparent from POV of non-existent node`` () =
63
- fromPOV x (leaf "foo") |> should equal None
60
+ let ``Errors if target does not exist in a large tree`` () =
61
+ let tree = mkGraph "parent" [mkGraph "x" [mkGraph "kid-0" []; mkGraph "kid-1" []]; mkGraph "sibling-0" []; mkGraph "sibling-1" []]
62
+ fromPOV "nonexistent" tree |> should equal None
64
63
 
65
64
  [<Fact(Skip = "Remove to run test")>]
66
- let ``Should not be able to find a missing node`` () =
67
- let nodes = [singleton; flat; kids; nested; cousins] |> List.map (fromPOV "NOT THERE")
68
- nodes |> List.iter (should equal None)
65
+ let ``Can find path to parent`` () =
66
+ let tree = mkGraph "parent" [mkGraph "x" []; mkGraph "sibling" []]
67
+ tracePathBetween "x" "parent" tree |> should equal <| Some ["x"; "parent"]
69
68
 
70
69
  [<Fact(Skip = "Remove to run test")>]
71
- let ``Cannot trace between un-connected nodes`` () =
72
- tracePathBetween x "NOT THERE" cousins |> should equal None
70
+ let ``Can find path to sibling`` () =
71
+ let tree = mkGraph "parent" [mkGraph "a" []; mkGraph "x" []; mkGraph "b" []; mkGraph "c" []]
72
+ tracePathBetween "x" "b" tree |> should equal <| Some ["x"; "parent"; "b"]
73
73
 
74
74
  [<Fact(Skip = "Remove to run test")>]
75
- let ``Can trace a path from x to cousin`` () =
76
- tracePathBetween x "cousin-1" cousins |> should equal <| Some ["x"; "parent"; "grandparent"; "uncle"; "cousin-1"]
75
+ let ``Can find path to cousin`` () =
76
+ let tree = mkGraph "grandparent" [mkGraph "parent" [mkGraph "x" [mkGraph "kid-0" []; mkGraph "kid-1" []]; mkGraph "sibling-0" []; mkGraph "sibling-1" []]; mkGraph "uncle" [mkGraph "cousin-0" []; mkGraph "cousin-1" []]]
77
+ tracePathBetween "x" "cousin-1" tree |> should equal <| Some ["x"; "parent"; "grandparent"; "uncle"; "cousin-1"]
77
78
 
78
79
  [<Fact(Skip = "Remove to run test")>]
79
- let ``Can trace from a leaf to a leaf`` () =
80
- tracePathBetween "kid-a" "cousin-0" cousins |> should equal <| Some ["kid-a"; "x"; "parent"; "grandparent"; "uncle"; "cousin-0"]
80
+ let ``Can find path from nodes other than x`` () =
81
+ let tree = mkGraph "parent" [mkGraph "a" []; mkGraph "x" []; mkGraph "b" []; mkGraph "c" []]
82
+ tracePathBetween "a" "c" tree |> should equal <| Some ["a"; "parent"; "c"]
83
+
84
+ [<Fact(Skip = "Remove to run test")>]
85
+ let ``Errors if destination does not exist`` () =
86
+ let tree = mkGraph "parent" [mkGraph "x" [mkGraph "kid-0" []; mkGraph "kid-1" []]; mkGraph "sibling-0" []; mkGraph "sibling-1" []]
87
+ tracePathBetween "x" "nonexistent" tree |> should equal None
88
+
89
+ [<Fact(Skip = "Remove to run test")>]
90
+ let ``Errors if source does not exist`` () =
91
+ let tree = mkGraph "parent" [mkGraph "x" [mkGraph "kid-0" []; mkGraph "kid-1" []]; mkGraph "sibling-0" []; mkGraph "sibling-1" []]
92
+ tracePathBetween "nonexistent" "x" tree |> should equal None
93
+
@@ -12,20 +12,20 @@ type Planet =
12
12
  | Neptune
13
13
  | Uranus
14
14
 
15
- let secondsOnEarth = 31557600m
15
+ let secondsOnEarth = 31557600.0
16
16
 
17
17
  let planetPeriods =
18
- [Mercury, 0.2408467m;
19
- Venus, 0.61519726m;
20
- Earth, 1.0m;
21
- Mars, 1.8808158m;
22
- Jupiter, 11.862615m;
23
- Saturn, 29.447498m;
24
- Uranus, 84.016846m;
25
- Neptune, 164.79132m]
18
+ [Mercury, 0.2408467;
19
+ Venus, 0.61519726;
20
+ Earth, 1.0;
21
+ Mars, 1.8808158;
22
+ Jupiter, 11.862615;
23
+ Saturn, 29.447498;
24
+ Uranus, 84.016846;
25
+ Neptune, 164.79132]
26
26
  |> Map.ofList
27
27
 
28
- let spaceAge planet (seconds: decimal) =
29
- let yearsUsingPeriod (period:decimal) = Math.Round((seconds / period) / secondsOnEarth, 2)
28
+ let age planet (seconds: int64) =
29
+ let yearsUsingPeriod (period: float) = Math.Round((float seconds / period) / secondsOnEarth, 2)
30
30
 
31
31
  yearsUsingPeriod planetPeriods.[planet]
@@ -2,4 +2,4 @@
2
2
 
3
3
  // TODO: define the Planet type
4
4
 
5
- let spaceAge (planet: Planet) (seconds: decimal): decimal = failwith "You need to implement this function."
5
+ let age (planet: Planet) (seconds: int64): float = failwith "You need to implement this function."
@@ -1,54 +1,41 @@
1
- // This file was created manually and its version is 1.0.0.
1
+ // This file was auto-generated based on version 1.1.0 of the canonical data.
2
2
 
3
3
  module SpaceAgeTest
4
4
 
5
- open Xunit
6
5
  open FsUnit.Xunit
6
+ open Xunit
7
+
7
8
  open SpaceAge
8
-
9
+
9
10
  [<Fact>]
10
- let ``Age on earth`` () =
11
- let seconds = 1000000000m
12
- spaceAge Planet.Earth seconds |> should equal 31.69m
11
+ let ``Age on Earth`` () =
12
+ age Earth 1000000000L |> should equal 31.69
13
13
 
14
14
  [<Fact(Skip = "Remove to run test")>]
15
- let ``Age on mercury`` () =
16
- let seconds = 2134835688m
17
- spaceAge Planet.Earth seconds |> should equal 67.65m
18
- spaceAge Planet.Mercury seconds |> should equal 280.88m
15
+ let ``Age on Mercury`` () =
16
+ age Mercury 2134835688L |> should equal 280.88
19
17
 
20
18
  [<Fact(Skip = "Remove to run test")>]
21
- let ``Age on venus`` () =
22
- let seconds = 189839836m
23
- spaceAge Planet.Earth seconds |> should equal 6.02m
24
- spaceAge Planet.Venus seconds |> should equal 9.78m
19
+ let ``Age on Venus`` () =
20
+ age Venus 189839836L |> should equal 9.78
25
21
 
26
22
  [<Fact(Skip = "Remove to run test")>]
27
- let ``Age on mars`` () =
28
- let seconds = 2329871239m
29
- spaceAge Planet.Earth seconds |> should equal 73.83m
30
- spaceAge Planet.Mars seconds |> should equal 39.25m
23
+ let ``Age on Mars`` () =
24
+ age Mars 2329871239L |> should equal 39.25
31
25
 
32
26
  [<Fact(Skip = "Remove to run test")>]
33
- let ``Age on jupiter`` () =
34
- let seconds = 901876382m
35
- spaceAge Planet.Earth seconds |> should equal 28.58m
36
- spaceAge Planet.Jupiter seconds |> should equal 2.41m
27
+ let ``Age on Jupiter`` () =
28
+ age Jupiter 901876382L |> should equal 2.41
37
29
 
38
30
  [<Fact(Skip = "Remove to run test")>]
39
- let ``Age on saturn`` () =
40
- let seconds = 3000000000m
41
- spaceAge Planet.Earth seconds |> should equal 95.06m
42
- spaceAge Planet.Saturn seconds |> should equal 3.23m
31
+ let ``Age on Saturn`` () =
32
+ age Saturn 3000000000L |> should equal 3.23
43
33
 
44
34
  [<Fact(Skip = "Remove to run test")>]
45
- let ``Age on uranus`` () =
46
- let seconds = 3210123456m
47
- spaceAge Planet.Earth seconds |> should equal 101.72m
48
- spaceAge Planet.Uranus seconds |> should equal 1.21m
35
+ let ``Age on Uranus`` () =
36
+ age Uranus 3210123456L |> should equal 1.21
49
37
 
50
38
  [<Fact(Skip = "Remove to run test")>]
51
- let ``Age on neptune`` () =
52
- let seconds = 8210123456m
53
- spaceAge Planet.Earth seconds |> should equal 260.16m
54
- spaceAge Planet.Neptune seconds |> should equal 1.58m
39
+ let ``Age on Neptune`` () =
40
+ age Neptune 8210123456L |> should equal 1.58
41
+
@@ -1,22 +1,17 @@
1
1
  module Triangle
2
2
 
3
- open System
3
+ let private isValid triangle =
4
+ let nonZero = List.sum triangle <> 0.0
5
+ let equality =
6
+ let [x; y; z] = triangle
7
+ x + y >= z && x + z >= y && y + z >= x
8
+
9
+ equality && nonZero
4
10
 
5
- type TriangleKind =
6
- | Equilateral
7
- | Isosceles
8
- | Scalene
11
+ let private distinctSides triangle = triangle |> List.distinct |> List.length
9
12
 
10
- let kind (x: decimal) (y: decimal) (z: decimal) =
11
- let hasZeroSides = x = 0m && y = 0m && z = 0m
12
- let hasNegativeSide = x < 0m || y < 0m || z < 0m
13
- let violatesTriangleEquality = x + y <= z || x + z <= y || y + z <= x
13
+ let equilateral triangle = isValid triangle && distinctSides triangle = 1
14
14
 
15
- let isInvalid = hasZeroSides || hasNegativeSide || violatesTriangleEquality
16
- let isEquilateral = x = y && y = z
17
- let isIsosceles = x = y || y = z || x = z
15
+ let isosceles triangle = isValid triangle && distinctSides triangle <= 2
18
16
 
19
- if isInvalid then invalidOp "Invalid triangle."
20
- elif isEquilateral then TriangleKind.Equilateral
21
- elif isIsosceles then TriangleKind.Isosceles
22
- else TriangleKind.Scalene
17
+ let scalene triangle = isValid triangle && distinctSides triangle = 3
@@ -1,8 +1,7 @@
1
1
  module Triangle
2
2
 
3
- type TriangleKind =
4
- | Equilateral
5
- | Isosceles
6
- | Scalene
3
+ let equilateral triangle = failwith "You need to implement this function."
7
4
 
8
- let kind x y z = failwith "You need to implement this function."
5
+ let isosceles triangle = failwith "You need to implement this function."
6
+
7
+ let scalene triangle = failwith "You need to implement this function."
@@ -1,64 +1,77 @@
1
- // This file was created manually and its version is 1.0.0.
1
+ // This file was auto-generated based on version 1.1.0 of the canonical data.
2
2
 
3
3
  module TriangleTest
4
4
 
5
- open Xunit
6
5
  open FsUnit.Xunit
6
+ open Xunit
7
+
7
8
  open Triangle
8
- open System
9
9
 
10
10
  [<Fact>]
11
- let ``Equilateral triangles have equal sides`` () =
12
- kind 2m 2m 2m |> should equal TriangleKind.Equilateral
11
+ let ``Equilateral returns true if all sides are equal`` () =
12
+ equilateral [2.0; 2.0; 2.0] |> should equal true
13
+
14
+ [<Fact(Skip = "Remove to run test")>]
15
+ let ``Equilateral returns false if any side is unequal`` () =
16
+ equilateral [2.0; 3.0; 2.0] |> should equal false
13
17
 
14
18
  [<Fact(Skip = "Remove to run test")>]
15
- let ``Larger equilateral triangles also have equal sides`` () =
16
- kind 10m 10m 10m |> should equal TriangleKind.Equilateral
19
+ let ``Equilateral returns false if no sides are equal`` () =
20
+ equilateral [5.0; 4.0; 6.0] |> should equal false
17
21
 
18
22
  [<Fact(Skip = "Remove to run test")>]
19
- let ``Isosceles triangles have last two sides equal`` () =
20
- kind 3m 4m 4m |> should equal TriangleKind.Isosceles
23
+ let ``All zero sides are illegal, so the triangle is not equilateral`` () =
24
+ equilateral [0.0; 0.0; 0.0] |> should equal false
21
25
 
22
26
  [<Fact(Skip = "Remove to run test")>]
23
- let ``Isosceles triangles have first and last sides equal`` () =
24
- kind 4m 3m 4m |> should equal TriangleKind.Isosceles
27
+ let ``Equilateral returns sides may be floats`` () =
28
+ equilateral [0.5; 0.5; 0.5] |> should equal true
25
29
 
26
30
  [<Fact(Skip = "Remove to run test")>]
27
- let ``Isosceles triangles have two first sides equal`` () =
28
- kind 4m 4m 3m |> should equal TriangleKind.Isosceles
31
+ let ``Isosceles returns true if last two sides are equal`` () =
32
+ isosceles [3.0; 4.0; 4.0] |> should equal true
29
33
 
30
34
  [<Fact(Skip = "Remove to run test")>]
31
- let ``Isosceles triangles have in fact exactly two sides equal`` () =
32
- kind 10m 10m 3m |> should equal TriangleKind.Isosceles
35
+ let ``Isosceles returns true if first two sides are equal`` () =
36
+ isosceles [4.0; 4.0; 3.0] |> should equal true
33
37
 
34
38
  [<Fact(Skip = "Remove to run test")>]
35
- let ``Scalene triangles have no equal sides`` () =
36
- kind 3m 4m 5m |> should equal TriangleKind.Scalene
39
+ let ``Isosceles returns true if first and last sides are equal`` () =
40
+ isosceles [4.0; 3.0; 4.0] |> should equal true
37
41
 
38
42
  [<Fact(Skip = "Remove to run test")>]
39
- let ``Scalene triangles have no equal sides at a larger scale too`` () =
40
- kind 10m 11m 12m |> should equal TriangleKind.Scalene
43
+ let ``Equilateral triangles are also isosceles`` () =
44
+ isosceles [4.0; 4.0; 4.0] |> should equal true
41
45
 
42
46
  [<Fact(Skip = "Remove to run test")>]
43
- let ``Scalene triangles have no equal sides in descending order either`` () =
44
- kind 5m 4m 2m |> should equal TriangleKind.Scalene
47
+ let ``Isosceles returns false if no sides are equal`` () =
48
+ isosceles [2.0; 3.0; 4.0] |> should equal false
45
49
 
46
50
  [<Fact(Skip = "Remove to run test")>]
47
- let ``Very small triangles are legal`` () =
48
- kind 0.4m 0.6m 0.3m |> should equal TriangleKind.Scalene
51
+ let ``Sides that violate triangle inequality are not isosceles, even if two are equal`` () =
52
+ isosceles [1.0; 1.0; 3.0] |> should equal false
49
53
 
50
54
  [<Fact(Skip = "Remove to run test")>]
51
- let ``Triangles with no size are illegal`` () =
52
- (fun () -> kind 0m 0m 0m |> ignore) |> should throw typeof<InvalidOperationException>
55
+ let ``Isosceles returns sides may be floats`` () =
56
+ isosceles [0.5; 0.4; 0.5] |> should equal true
53
57
 
54
58
  [<Fact(Skip = "Remove to run test")>]
55
- let ``Triangles with negative sides are illegal`` () =
56
- (fun () -> kind 3m 4m -5m |> ignore) |> should throw typeof<InvalidOperationException>
59
+ let ``Scalene returns true if no sides are equal`` () =
60
+ scalene [5.0; 4.0; 6.0] |> should equal true
57
61
 
58
62
  [<Fact(Skip = "Remove to run test")>]
59
- let ``Triangles violating triangle inequality are illegal`` () =
60
- (fun () -> kind 1m 1m 3m |> ignore) |> should throw typeof<InvalidOperationException>
63
+ let ``Scalene returns false if all sides are equal`` () =
64
+ scalene [4.0; 4.0; 4.0] |> should equal false
61
65
 
62
66
  [<Fact(Skip = "Remove to run test")>]
63
- let ``Triangles violating triangle inequality are illegal 3`` () =
64
- (fun () -> kind 7m 3m 2m |> ignore) |> should throw typeof<InvalidOperationException>
67
+ let ``Scalene returns false if two sides are equal`` () =
68
+ scalene [4.0; 4.0; 3.0] |> should equal false
69
+
70
+ [<Fact(Skip = "Remove to run test")>]
71
+ let ``Sides that violate triangle inequality are not scalene, even if they are all different`` () =
72
+ scalene [7.0; 3.0; 2.0] |> should equal false
73
+
74
+ [<Fact(Skip = "Remove to run test")>]
75
+ let ``Scalene returns sides may be floats`` () =
76
+ scalene [0.5; 0.4; 0.6] |> should equal true
77
+
@@ -789,6 +789,92 @@ type Poker() =
789
789
 
790
790
  override __.PropertiesWithIdentifier _ = ["input"; "expected"]
791
791
 
792
+ type Pov() =
793
+ inherit GeneratorExercise()
794
+
795
+ let isNull x = match x with null -> true | _ -> false
796
+
797
+ override __.RenderSetup _ =
798
+ ["let rec graphToList graph = "
799
+ " let right ="
800
+ " graph.children"
801
+ " |> List.sortBy (fun x -> x.value)"
802
+ " |> List.collect graphToList"
803
+ " [graph.value] @ right"
804
+ "let mapToList graph = match graph with | Some x -> graphToList x | None -> []"
805
+ ] |> String.concat "\n"
806
+
807
+ member this.RenderNode (tree: obj) : string =
808
+ match isNull tree with
809
+ | true -> ""
810
+ | false ->
811
+ let node = (tree :?> JObject).ToObject<Collections.Generic.Dictionary<string, JToken>>();
812
+ let children =
813
+ if node.ContainsKey "children" then
814
+ node.["children"]
815
+ |> Seq.map this.RenderNode
816
+ |> formatList
817
+ else
818
+ "[]"
819
+ let label =
820
+ node.["label"]
821
+ |> formatValue
822
+ sprintf "mkGraph %s %s" label children
823
+
824
+ override this.RenderArrange canonicalDataCase =
825
+ seq {
826
+ yield
827
+ canonicalDataCase.Properties.["tree"]
828
+ |> this.RenderNode
829
+ |> sprintf "let tree = %s"
830
+
831
+ match canonicalDataCase.Property, isNull canonicalDataCase.Expected with
832
+ | "fromPov", false ->
833
+ yield
834
+ canonicalDataCase.Expected
835
+ |> this.RenderNode
836
+ |> sprintf "let expected = %s"
837
+ | _, _ -> ()
838
+ }
839
+ |> Seq.toList
840
+
841
+
842
+ override __.RenderSut canonicalDataCase =
843
+ match canonicalDataCase.Property with
844
+ | "fromPov" ->
845
+ let from =
846
+ canonicalDataCase.Properties.["from"]
847
+ |> formatValue
848
+ match isNull canonicalDataCase.Expected with
849
+ | false -> sprintf "fromPOV %s tree |> mapToList " from
850
+ | true -> sprintf "fromPOV %s tree " from
851
+ | "pathTo" ->
852
+ let fromValue =
853
+ canonicalDataCase.Properties.["from"]
854
+ |> formatValue
855
+ let toValue =
856
+ canonicalDataCase.Properties.["to"]
857
+ |> formatValue
858
+ sprintf "tracePathBetween %s %s tree" fromValue toValue
859
+ | _ -> ""
860
+
861
+ override __.RenderExpected (canonicalDataCase, key, value) =
862
+ match canonicalDataCase.Property with
863
+ | "fromPov" ->
864
+ match isNull value with
865
+ | true -> "None"
866
+ | false -> sprintf "<| graphToList %s" key
867
+ | "pathTo" ->
868
+ match isNull value with
869
+ | true -> "None"
870
+ | false ->
871
+ printf "%s" canonicalDataCase.Description
872
+ canonicalDataCase.Expected :?> JArray
873
+ |> Seq.map formatValue
874
+ |> formatList
875
+ |> sprintf "<| Some %s"
876
+ | _ -> ""
877
+
792
878
  type PrimeFactors() =
793
879
  inherit GeneratorExercise()
794
880
 
@@ -1065,6 +1151,15 @@ type Sieve() =
1065
1151
  type SecretHandshake() =
1066
1152
  inherit GeneratorExercise()
1067
1153
 
1154
+ type SpaceAge() =
1155
+ inherit GeneratorExercise()
1156
+
1157
+ override __.RenderInput (canonicalDataCase, key, value) =
1158
+ match value with
1159
+ | :? string as s -> s
1160
+ | :? int64 as i -> sprintf "%dL" i
1161
+ | _ -> base.RenderInput (canonicalDataCase, key, value)
1162
+
1068
1163
  type SpiralMatrix() =
1069
1164
  inherit GeneratorExercise()
1070
1165
 
@@ -1088,6 +1183,32 @@ type TwelveDays() =
1088
1183
  |> Seq.map formatValue
1089
1184
  |> formatMultiLineList
1090
1185
 
1186
+ type Triangle() =
1187
+ inherit GeneratorExercise()
1188
+
1189
+ let formatFloat (value:obj) =
1190
+ match value with
1191
+ | :? int64 as i -> sprintf "%.1f" (float i)
1192
+ | :? int32 as i -> sprintf "%.1f" (float i)
1193
+ | :? float as f -> sprintf "%.1f" f
1194
+ | _ -> failwith "Invalid value"
1195
+
1196
+ let hasUniqueTestMethodName canonicalDataCase =
1197
+ canonicalDataCase.Description.Contains "equilateral" ||
1198
+ canonicalDataCase.Description.Contains "isosceles" ||
1199
+ canonicalDataCase.Description.Contains "scalene"
1200
+
1201
+ override __.RenderTestMethodName canonicalDataCase =
1202
+ match hasUniqueTestMethodName canonicalDataCase with
1203
+ | true -> base.RenderTestMethodName canonicalDataCase
1204
+ | false -> sprintf "%s returns %s" (String.upperCaseFirst canonicalDataCase.Property) canonicalDataCase.Description
1205
+
1206
+ override __.RenderInput (_, _, value) =
1207
+ value :?> JArray
1208
+ |> normalizeJArray
1209
+ |> Seq.map formatFloat
1210
+ |> formatList
1211
+
1091
1212
  type TwoFer() =
1092
1213
  inherit GeneratorExercise()
1093
1214