| @@ -0,0 +1,31 @@ | |||
| module BeerSong | |||
| let stateLine n = | |||
| if n > 1 | |||
| then sprintf "%d bottles of beer on the wall, %d bottles of beer." n n | |||
| else if n = 1 | |||
| then "1 bottle of beer on the wall, 1 bottle of beer." | |||
| else "No more bottles of beer on the wall, no more bottles of beer." | |||
| let takeDownLine n = | |||
| if n > 2 | |||
| then sprintf "Take one down and pass it around, %d bottles of beer on the wall." (n - 1) | |||
| else if n = 2 | |||
| then "Take one down and pass it around, 1 bottle of beer on the wall." | |||
| else if n = 1 | |||
| then "Take it down and pass it around, no more bottles of beer on the wall." | |||
| else "Go to the store and buy some more, 99 bottles of beer on the wall." | |||
| let verse (n: int) (left: int) = | |||
| if left > 1 then [ stateLine n; takeDownLine n; "" ] else [ stateLine n; takeDownLine n ] | |||
| let rec beerLines (n: int) (left: int): list<string> = | |||
| let newBottles = if n = 0 then 99 else n - 1 // wrap around when get to 0 | |||
| if left > 0 && n >= 0 then | |||
| List.concat | |||
| [ (verse n left) | |||
| (beerLines newBottles (left - 1)) ] | |||
| else | |||
| [] | |||
| let recite (startBottles: int) (takeDown: int) = beerLines startBottles takeDown | |||
| @@ -0,0 +1,21 @@ | |||
| <Project Sdk="Microsoft.NET.Sdk"> | |||
| <PropertyGroup> | |||
| <TargetFramework>netcoreapp3.0</TargetFramework> | |||
| <IsPackable>false</IsPackable> | |||
| </PropertyGroup> | |||
| <ItemGroup> | |||
| <Compile Include="BeerSong.fs" /> | |||
| <Compile Include="BeerSongTests.fs" /> | |||
| </ItemGroup> | |||
| <ItemGroup> | |||
| <PackageReference Include="Microsoft.NET.Test.Sdk" Version="16.6.1" /> | |||
| <PackageReference Include="xunit" Version="2.4.1" /> | |||
| <PackageReference Include="xunit.runner.visualstudio" Version="2.4.1" /> | |||
| <PackageReference Include="FsUnit.xUnit" Version="3.8.1" /> | |||
| </ItemGroup> | |||
| </Project> | |||
| @@ -0,0 +1,371 @@ | |||
| // This file was auto-generated based on version 2.1.0 of the canonical data. | |||
| module BeerSongTests | |||
| open FsUnit.Xunit | |||
| open Xunit | |||
| open BeerSong | |||
| [<Fact>] | |||
| let ``First generic verse`` () = | |||
| let expected = | |||
| [ "99 bottles of beer on the wall, 99 bottles of beer."; | |||
| "Take one down and pass it around, 98 bottles of beer on the wall." ] | |||
| recite 99 1 |> should equal expected | |||
| [<Fact>] | |||
| let ``Last generic verse`` () = | |||
| let expected = | |||
| [ "3 bottles of beer on the wall, 3 bottles of beer."; | |||
| "Take one down and pass it around, 2 bottles of beer on the wall." ] | |||
| recite 3 1 |> should equal expected | |||
| [<Fact>] | |||
| let ``Verse with 2 bottles`` () = | |||
| let expected = | |||
| [ "2 bottles of beer on the wall, 2 bottles of beer."; | |||
| "Take one down and pass it around, 1 bottle of beer on the wall." ] | |||
| recite 2 1 |> should equal expected | |||
| [<Fact>] | |||
| let ``Verse with 1 bottle`` () = | |||
| let expected = | |||
| [ "1 bottle of beer on the wall, 1 bottle of beer."; | |||
| "Take it down and pass it around, no more bottles of beer on the wall." ] | |||
| recite 1 1 |> should equal expected | |||
| [<Fact>] | |||
| let ``Verse with 0 bottles`` () = | |||
| let expected = | |||
| [ "No more bottles of beer on the wall, no more bottles of beer."; | |||
| "Go to the store and buy some more, 99 bottles of beer on the wall." ] | |||
| recite 0 1 |> should equal expected | |||
| [<Fact>] | |||
| let ``First two verses`` () = | |||
| let expected = | |||
| [ "99 bottles of beer on the wall, 99 bottles of beer."; | |||
| "Take one down and pass it around, 98 bottles of beer on the wall."; | |||
| ""; | |||
| "98 bottles of beer on the wall, 98 bottles of beer."; | |||
| "Take one down and pass it around, 97 bottles of beer on the wall." ] | |||
| recite 99 2 |> should equal expected | |||
| [<Fact>] | |||
| let ``Last three verses`` () = | |||
| let expected = | |||
| [ "2 bottles of beer on the wall, 2 bottles of beer."; | |||
| "Take one down and pass it around, 1 bottle of beer on the wall."; | |||
| ""; | |||
| "1 bottle of beer on the wall, 1 bottle of beer."; | |||
| "Take it down and pass it around, no more bottles of beer on the wall."; | |||
| ""; | |||
| "No more bottles of beer on the wall, no more bottles of beer."; | |||
| "Go to the store and buy some more, 99 bottles of beer on the wall." ] | |||
| recite 2 3 |> should equal expected | |||
| [<Fact>] | |||
| let ``All verses`` () = | |||
| let expected = | |||
| [ "99 bottles of beer on the wall, 99 bottles of beer."; | |||
| "Take one down and pass it around, 98 bottles of beer on the wall."; | |||
| ""; | |||
| "98 bottles of beer on the wall, 98 bottles of beer."; | |||
| "Take one down and pass it around, 97 bottles of beer on the wall."; | |||
| ""; | |||
| "97 bottles of beer on the wall, 97 bottles of beer."; | |||
| "Take one down and pass it around, 96 bottles of beer on the wall."; | |||
| ""; | |||
| "96 bottles of beer on the wall, 96 bottles of beer."; | |||
| "Take one down and pass it around, 95 bottles of beer on the wall."; | |||
| ""; | |||
| "95 bottles of beer on the wall, 95 bottles of beer."; | |||
| "Take one down and pass it around, 94 bottles of beer on the wall."; | |||
| ""; | |||
| "94 bottles of beer on the wall, 94 bottles of beer."; | |||
| "Take one down and pass it around, 93 bottles of beer on the wall."; | |||
| ""; | |||
| "93 bottles of beer on the wall, 93 bottles of beer."; | |||
| "Take one down and pass it around, 92 bottles of beer on the wall."; | |||
| ""; | |||
| "92 bottles of beer on the wall, 92 bottles of beer."; | |||
| "Take one down and pass it around, 91 bottles of beer on the wall."; | |||
| ""; | |||
| "91 bottles of beer on the wall, 91 bottles of beer."; | |||
| "Take one down and pass it around, 90 bottles of beer on the wall."; | |||
| ""; | |||
| "90 bottles of beer on the wall, 90 bottles of beer."; | |||
| "Take one down and pass it around, 89 bottles of beer on the wall."; | |||
| ""; | |||
| "89 bottles of beer on the wall, 89 bottles of beer."; | |||
| "Take one down and pass it around, 88 bottles of beer on the wall."; | |||
| ""; | |||
| "88 bottles of beer on the wall, 88 bottles of beer."; | |||
| "Take one down and pass it around, 87 bottles of beer on the wall."; | |||
| ""; | |||
| "87 bottles of beer on the wall, 87 bottles of beer."; | |||
| "Take one down and pass it around, 86 bottles of beer on the wall."; | |||
| ""; | |||
| "86 bottles of beer on the wall, 86 bottles of beer."; | |||
| "Take one down and pass it around, 85 bottles of beer on the wall."; | |||
| ""; | |||
| "85 bottles of beer on the wall, 85 bottles of beer."; | |||
| "Take one down and pass it around, 84 bottles of beer on the wall."; | |||
| ""; | |||
| "84 bottles of beer on the wall, 84 bottles of beer."; | |||
| "Take one down and pass it around, 83 bottles of beer on the wall."; | |||
| ""; | |||
| "83 bottles of beer on the wall, 83 bottles of beer."; | |||
| "Take one down and pass it around, 82 bottles of beer on the wall."; | |||
| ""; | |||
| "82 bottles of beer on the wall, 82 bottles of beer."; | |||
| "Take one down and pass it around, 81 bottles of beer on the wall."; | |||
| ""; | |||
| "81 bottles of beer on the wall, 81 bottles of beer."; | |||
| "Take one down and pass it around, 80 bottles of beer on the wall."; | |||
| ""; | |||
| "80 bottles of beer on the wall, 80 bottles of beer."; | |||
| "Take one down and pass it around, 79 bottles of beer on the wall."; | |||
| ""; | |||
| "79 bottles of beer on the wall, 79 bottles of beer."; | |||
| "Take one down and pass it around, 78 bottles of beer on the wall."; | |||
| ""; | |||
| "78 bottles of beer on the wall, 78 bottles of beer."; | |||
| "Take one down and pass it around, 77 bottles of beer on the wall."; | |||
| ""; | |||
| "77 bottles of beer on the wall, 77 bottles of beer."; | |||
| "Take one down and pass it around, 76 bottles of beer on the wall."; | |||
| ""; | |||
| "76 bottles of beer on the wall, 76 bottles of beer."; | |||
| "Take one down and pass it around, 75 bottles of beer on the wall."; | |||
| ""; | |||
| "75 bottles of beer on the wall, 75 bottles of beer."; | |||
| "Take one down and pass it around, 74 bottles of beer on the wall."; | |||
| ""; | |||
| "74 bottles of beer on the wall, 74 bottles of beer."; | |||
| "Take one down and pass it around, 73 bottles of beer on the wall."; | |||
| ""; | |||
| "73 bottles of beer on the wall, 73 bottles of beer."; | |||
| "Take one down and pass it around, 72 bottles of beer on the wall."; | |||
| ""; | |||
| "72 bottles of beer on the wall, 72 bottles of beer."; | |||
| "Take one down and pass it around, 71 bottles of beer on the wall."; | |||
| ""; | |||
| "71 bottles of beer on the wall, 71 bottles of beer."; | |||
| "Take one down and pass it around, 70 bottles of beer on the wall."; | |||
| ""; | |||
| "70 bottles of beer on the wall, 70 bottles of beer."; | |||
| "Take one down and pass it around, 69 bottles of beer on the wall."; | |||
| ""; | |||
| "69 bottles of beer on the wall, 69 bottles of beer."; | |||
| "Take one down and pass it around, 68 bottles of beer on the wall."; | |||
| ""; | |||
| "68 bottles of beer on the wall, 68 bottles of beer."; | |||
| "Take one down and pass it around, 67 bottles of beer on the wall."; | |||
| ""; | |||
| "67 bottles of beer on the wall, 67 bottles of beer."; | |||
| "Take one down and pass it around, 66 bottles of beer on the wall."; | |||
| ""; | |||
| "66 bottles of beer on the wall, 66 bottles of beer."; | |||
| "Take one down and pass it around, 65 bottles of beer on the wall."; | |||
| ""; | |||
| "65 bottles of beer on the wall, 65 bottles of beer."; | |||
| "Take one down and pass it around, 64 bottles of beer on the wall."; | |||
| ""; | |||
| "64 bottles of beer on the wall, 64 bottles of beer."; | |||
| "Take one down and pass it around, 63 bottles of beer on the wall."; | |||
| ""; | |||
| "63 bottles of beer on the wall, 63 bottles of beer."; | |||
| "Take one down and pass it around, 62 bottles of beer on the wall."; | |||
| ""; | |||
| "62 bottles of beer on the wall, 62 bottles of beer."; | |||
| "Take one down and pass it around, 61 bottles of beer on the wall."; | |||
| ""; | |||
| "61 bottles of beer on the wall, 61 bottles of beer."; | |||
| "Take one down and pass it around, 60 bottles of beer on the wall."; | |||
| ""; | |||
| "60 bottles of beer on the wall, 60 bottles of beer."; | |||
| "Take one down and pass it around, 59 bottles of beer on the wall."; | |||
| ""; | |||
| "59 bottles of beer on the wall, 59 bottles of beer."; | |||
| "Take one down and pass it around, 58 bottles of beer on the wall."; | |||
| ""; | |||
| "58 bottles of beer on the wall, 58 bottles of beer."; | |||
| "Take one down and pass it around, 57 bottles of beer on the wall."; | |||
| ""; | |||
| "57 bottles of beer on the wall, 57 bottles of beer."; | |||
| "Take one down and pass it around, 56 bottles of beer on the wall."; | |||
| ""; | |||
| "56 bottles of beer on the wall, 56 bottles of beer."; | |||
| "Take one down and pass it around, 55 bottles of beer on the wall."; | |||
| ""; | |||
| "55 bottles of beer on the wall, 55 bottles of beer."; | |||
| "Take one down and pass it around, 54 bottles of beer on the wall."; | |||
| ""; | |||
| "54 bottles of beer on the wall, 54 bottles of beer."; | |||
| "Take one down and pass it around, 53 bottles of beer on the wall."; | |||
| ""; | |||
| "53 bottles of beer on the wall, 53 bottles of beer."; | |||
| "Take one down and pass it around, 52 bottles of beer on the wall."; | |||
| ""; | |||
| "52 bottles of beer on the wall, 52 bottles of beer."; | |||
| "Take one down and pass it around, 51 bottles of beer on the wall."; | |||
| ""; | |||
| "51 bottles of beer on the wall, 51 bottles of beer."; | |||
| "Take one down and pass it around, 50 bottles of beer on the wall."; | |||
| ""; | |||
| "50 bottles of beer on the wall, 50 bottles of beer."; | |||
| "Take one down and pass it around, 49 bottles of beer on the wall."; | |||
| ""; | |||
| "49 bottles of beer on the wall, 49 bottles of beer."; | |||
| "Take one down and pass it around, 48 bottles of beer on the wall."; | |||
| ""; | |||
| "48 bottles of beer on the wall, 48 bottles of beer."; | |||
| "Take one down and pass it around, 47 bottles of beer on the wall."; | |||
| ""; | |||
| "47 bottles of beer on the wall, 47 bottles of beer."; | |||
| "Take one down and pass it around, 46 bottles of beer on the wall."; | |||
| ""; | |||
| "46 bottles of beer on the wall, 46 bottles of beer."; | |||
| "Take one down and pass it around, 45 bottles of beer on the wall."; | |||
| ""; | |||
| "45 bottles of beer on the wall, 45 bottles of beer."; | |||
| "Take one down and pass it around, 44 bottles of beer on the wall."; | |||
| ""; | |||
| "44 bottles of beer on the wall, 44 bottles of beer."; | |||
| "Take one down and pass it around, 43 bottles of beer on the wall."; | |||
| ""; | |||
| "43 bottles of beer on the wall, 43 bottles of beer."; | |||
| "Take one down and pass it around, 42 bottles of beer on the wall."; | |||
| ""; | |||
| "42 bottles of beer on the wall, 42 bottles of beer."; | |||
| "Take one down and pass it around, 41 bottles of beer on the wall."; | |||
| ""; | |||
| "41 bottles of beer on the wall, 41 bottles of beer."; | |||
| "Take one down and pass it around, 40 bottles of beer on the wall."; | |||
| ""; | |||
| "40 bottles of beer on the wall, 40 bottles of beer."; | |||
| "Take one down and pass it around, 39 bottles of beer on the wall."; | |||
| ""; | |||
| "39 bottles of beer on the wall, 39 bottles of beer."; | |||
| "Take one down and pass it around, 38 bottles of beer on the wall."; | |||
| ""; | |||
| "38 bottles of beer on the wall, 38 bottles of beer."; | |||
| "Take one down and pass it around, 37 bottles of beer on the wall."; | |||
| ""; | |||
| "37 bottles of beer on the wall, 37 bottles of beer."; | |||
| "Take one down and pass it around, 36 bottles of beer on the wall."; | |||
| ""; | |||
| "36 bottles of beer on the wall, 36 bottles of beer."; | |||
| "Take one down and pass it around, 35 bottles of beer on the wall."; | |||
| ""; | |||
| "35 bottles of beer on the wall, 35 bottles of beer."; | |||
| "Take one down and pass it around, 34 bottles of beer on the wall."; | |||
| ""; | |||
| "34 bottles of beer on the wall, 34 bottles of beer."; | |||
| "Take one down and pass it around, 33 bottles of beer on the wall."; | |||
| ""; | |||
| "33 bottles of beer on the wall, 33 bottles of beer."; | |||
| "Take one down and pass it around, 32 bottles of beer on the wall."; | |||
| ""; | |||
| "32 bottles of beer on the wall, 32 bottles of beer."; | |||
| "Take one down and pass it around, 31 bottles of beer on the wall."; | |||
| ""; | |||
| "31 bottles of beer on the wall, 31 bottles of beer."; | |||
| "Take one down and pass it around, 30 bottles of beer on the wall."; | |||
| ""; | |||
| "30 bottles of beer on the wall, 30 bottles of beer."; | |||
| "Take one down and pass it around, 29 bottles of beer on the wall."; | |||
| ""; | |||
| "29 bottles of beer on the wall, 29 bottles of beer."; | |||
| "Take one down and pass it around, 28 bottles of beer on the wall."; | |||
| ""; | |||
| "28 bottles of beer on the wall, 28 bottles of beer."; | |||
| "Take one down and pass it around, 27 bottles of beer on the wall."; | |||
| ""; | |||
| "27 bottles of beer on the wall, 27 bottles of beer."; | |||
| "Take one down and pass it around, 26 bottles of beer on the wall."; | |||
| ""; | |||
| "26 bottles of beer on the wall, 26 bottles of beer."; | |||
| "Take one down and pass it around, 25 bottles of beer on the wall."; | |||
| ""; | |||
| "25 bottles of beer on the wall, 25 bottles of beer."; | |||
| "Take one down and pass it around, 24 bottles of beer on the wall."; | |||
| ""; | |||
| "24 bottles of beer on the wall, 24 bottles of beer."; | |||
| "Take one down and pass it around, 23 bottles of beer on the wall."; | |||
| ""; | |||
| "23 bottles of beer on the wall, 23 bottles of beer."; | |||
| "Take one down and pass it around, 22 bottles of beer on the wall."; | |||
| ""; | |||
| "22 bottles of beer on the wall, 22 bottles of beer."; | |||
| "Take one down and pass it around, 21 bottles of beer on the wall."; | |||
| ""; | |||
| "21 bottles of beer on the wall, 21 bottles of beer."; | |||
| "Take one down and pass it around, 20 bottles of beer on the wall."; | |||
| ""; | |||
| "20 bottles of beer on the wall, 20 bottles of beer."; | |||
| "Take one down and pass it around, 19 bottles of beer on the wall."; | |||
| ""; | |||
| "19 bottles of beer on the wall, 19 bottles of beer."; | |||
| "Take one down and pass it around, 18 bottles of beer on the wall."; | |||
| ""; | |||
| "18 bottles of beer on the wall, 18 bottles of beer."; | |||
| "Take one down and pass it around, 17 bottles of beer on the wall."; | |||
| ""; | |||
| "17 bottles of beer on the wall, 17 bottles of beer."; | |||
| "Take one down and pass it around, 16 bottles of beer on the wall."; | |||
| ""; | |||
| "16 bottles of beer on the wall, 16 bottles of beer."; | |||
| "Take one down and pass it around, 15 bottles of beer on the wall."; | |||
| ""; | |||
| "15 bottles of beer on the wall, 15 bottles of beer."; | |||
| "Take one down and pass it around, 14 bottles of beer on the wall."; | |||
| ""; | |||
| "14 bottles of beer on the wall, 14 bottles of beer."; | |||
| "Take one down and pass it around, 13 bottles of beer on the wall."; | |||
| ""; | |||
| "13 bottles of beer on the wall, 13 bottles of beer."; | |||
| "Take one down and pass it around, 12 bottles of beer on the wall."; | |||
| ""; | |||
| "12 bottles of beer on the wall, 12 bottles of beer."; | |||
| "Take one down and pass it around, 11 bottles of beer on the wall."; | |||
| ""; | |||
| "11 bottles of beer on the wall, 11 bottles of beer."; | |||
| "Take one down and pass it around, 10 bottles of beer on the wall."; | |||
| ""; | |||
| "10 bottles of beer on the wall, 10 bottles of beer."; | |||
| "Take one down and pass it around, 9 bottles of beer on the wall."; | |||
| ""; | |||
| "9 bottles of beer on the wall, 9 bottles of beer."; | |||
| "Take one down and pass it around, 8 bottles of beer on the wall."; | |||
| ""; | |||
| "8 bottles of beer on the wall, 8 bottles of beer."; | |||
| "Take one down and pass it around, 7 bottles of beer on the wall."; | |||
| ""; | |||
| "7 bottles of beer on the wall, 7 bottles of beer."; | |||
| "Take one down and pass it around, 6 bottles of beer on the wall."; | |||
| ""; | |||
| "6 bottles of beer on the wall, 6 bottles of beer."; | |||
| "Take one down and pass it around, 5 bottles of beer on the wall."; | |||
| ""; | |||
| "5 bottles of beer on the wall, 5 bottles of beer."; | |||
| "Take one down and pass it around, 4 bottles of beer on the wall."; | |||
| ""; | |||
| "4 bottles of beer on the wall, 4 bottles of beer."; | |||
| "Take one down and pass it around, 3 bottles of beer on the wall."; | |||
| ""; | |||
| "3 bottles of beer on the wall, 3 bottles of beer."; | |||
| "Take one down and pass it around, 2 bottles of beer on the wall."; | |||
| ""; | |||
| "2 bottles of beer on the wall, 2 bottles of beer."; | |||
| "Take one down and pass it around, 1 bottle of beer on the wall."; | |||
| ""; | |||
| "1 bottle of beer on the wall, 1 bottle of beer."; | |||
| "Take it down and pass it around, no more bottles of beer on the wall."; | |||
| ""; | |||
| "No more bottles of beer on the wall, no more bottles of beer."; | |||
| "Go to the store and buy some more, 99 bottles of beer on the wall." ] | |||
| recite 99 100 |> should equal expected | |||
| @@ -0,0 +1,345 @@ | |||
| # Beer Song | |||
| Recite the lyrics to that beloved classic, that field-trip favorite: 99 Bottles of Beer on the Wall. | |||
| Note that not all verses are identical. | |||
| ```text | |||
| 99 bottles of beer on the wall, 99 bottles of beer. | |||
| Take one down and pass it around, 98 bottles of beer on the wall. | |||
| 98 bottles of beer on the wall, 98 bottles of beer. | |||
| Take one down and pass it around, 97 bottles of beer on the wall. | |||
| 97 bottles of beer on the wall, 97 bottles of beer. | |||
| Take one down and pass it around, 96 bottles of beer on the wall. | |||
| 96 bottles of beer on the wall, 96 bottles of beer. | |||
| Take one down and pass it around, 95 bottles of beer on the wall. | |||
| 95 bottles of beer on the wall, 95 bottles of beer. | |||
| Take one down and pass it around, 94 bottles of beer on the wall. | |||
| 94 bottles of beer on the wall, 94 bottles of beer. | |||
| Take one down and pass it around, 93 bottles of beer on the wall. | |||
| 93 bottles of beer on the wall, 93 bottles of beer. | |||
| Take one down and pass it around, 92 bottles of beer on the wall. | |||
| 92 bottles of beer on the wall, 92 bottles of beer. | |||
| Take one down and pass it around, 91 bottles of beer on the wall. | |||
| 91 bottles of beer on the wall, 91 bottles of beer. | |||
| Take one down and pass it around, 90 bottles of beer on the wall. | |||
| 90 bottles of beer on the wall, 90 bottles of beer. | |||
| Take one down and pass it around, 89 bottles of beer on the wall. | |||
| 89 bottles of beer on the wall, 89 bottles of beer. | |||
| Take one down and pass it around, 88 bottles of beer on the wall. | |||
| 88 bottles of beer on the wall, 88 bottles of beer. | |||
| Take one down and pass it around, 87 bottles of beer on the wall. | |||
| 87 bottles of beer on the wall, 87 bottles of beer. | |||
| Take one down and pass it around, 86 bottles of beer on the wall. | |||
| 86 bottles of beer on the wall, 86 bottles of beer. | |||
| Take one down and pass it around, 85 bottles of beer on the wall. | |||
| 85 bottles of beer on the wall, 85 bottles of beer. | |||
| Take one down and pass it around, 84 bottles of beer on the wall. | |||
| 84 bottles of beer on the wall, 84 bottles of beer. | |||
| Take one down and pass it around, 83 bottles of beer on the wall. | |||
| 83 bottles of beer on the wall, 83 bottles of beer. | |||
| Take one down and pass it around, 82 bottles of beer on the wall. | |||
| 82 bottles of beer on the wall, 82 bottles of beer. | |||
| Take one down and pass it around, 81 bottles of beer on the wall. | |||
| 81 bottles of beer on the wall, 81 bottles of beer. | |||
| Take one down and pass it around, 80 bottles of beer on the wall. | |||
| 80 bottles of beer on the wall, 80 bottles of beer. | |||
| Take one down and pass it around, 79 bottles of beer on the wall. | |||
| 79 bottles of beer on the wall, 79 bottles of beer. | |||
| Take one down and pass it around, 78 bottles of beer on the wall. | |||
| 78 bottles of beer on the wall, 78 bottles of beer. | |||
| Take one down and pass it around, 77 bottles of beer on the wall. | |||
| 77 bottles of beer on the wall, 77 bottles of beer. | |||
| Take one down and pass it around, 76 bottles of beer on the wall. | |||
| 76 bottles of beer on the wall, 76 bottles of beer. | |||
| Take one down and pass it around, 75 bottles of beer on the wall. | |||
| 75 bottles of beer on the wall, 75 bottles of beer. | |||
| Take one down and pass it around, 74 bottles of beer on the wall. | |||
| 74 bottles of beer on the wall, 74 bottles of beer. | |||
| Take one down and pass it around, 73 bottles of beer on the wall. | |||
| 73 bottles of beer on the wall, 73 bottles of beer. | |||
| Take one down and pass it around, 72 bottles of beer on the wall. | |||
| 72 bottles of beer on the wall, 72 bottles of beer. | |||
| Take one down and pass it around, 71 bottles of beer on the wall. | |||
| 71 bottles of beer on the wall, 71 bottles of beer. | |||
| Take one down and pass it around, 70 bottles of beer on the wall. | |||
| 70 bottles of beer on the wall, 70 bottles of beer. | |||
| Take one down and pass it around, 69 bottles of beer on the wall. | |||
| 69 bottles of beer on the wall, 69 bottles of beer. | |||
| Take one down and pass it around, 68 bottles of beer on the wall. | |||
| 68 bottles of beer on the wall, 68 bottles of beer. | |||
| Take one down and pass it around, 67 bottles of beer on the wall. | |||
| 67 bottles of beer on the wall, 67 bottles of beer. | |||
| Take one down and pass it around, 66 bottles of beer on the wall. | |||
| 66 bottles of beer on the wall, 66 bottles of beer. | |||
| Take one down and pass it around, 65 bottles of beer on the wall. | |||
| 65 bottles of beer on the wall, 65 bottles of beer. | |||
| Take one down and pass it around, 64 bottles of beer on the wall. | |||
| 64 bottles of beer on the wall, 64 bottles of beer. | |||
| Take one down and pass it around, 63 bottles of beer on the wall. | |||
| 63 bottles of beer on the wall, 63 bottles of beer. | |||
| Take one down and pass it around, 62 bottles of beer on the wall. | |||
| 62 bottles of beer on the wall, 62 bottles of beer. | |||
| Take one down and pass it around, 61 bottles of beer on the wall. | |||
| 61 bottles of beer on the wall, 61 bottles of beer. | |||
| Take one down and pass it around, 60 bottles of beer on the wall. | |||
| 60 bottles of beer on the wall, 60 bottles of beer. | |||
| Take one down and pass it around, 59 bottles of beer on the wall. | |||
| 59 bottles of beer on the wall, 59 bottles of beer. | |||
| Take one down and pass it around, 58 bottles of beer on the wall. | |||
| 58 bottles of beer on the wall, 58 bottles of beer. | |||
| Take one down and pass it around, 57 bottles of beer on the wall. | |||
| 57 bottles of beer on the wall, 57 bottles of beer. | |||
| Take one down and pass it around, 56 bottles of beer on the wall. | |||
| 56 bottles of beer on the wall, 56 bottles of beer. | |||
| Take one down and pass it around, 55 bottles of beer on the wall. | |||
| 55 bottles of beer on the wall, 55 bottles of beer. | |||
| Take one down and pass it around, 54 bottles of beer on the wall. | |||
| 54 bottles of beer on the wall, 54 bottles of beer. | |||
| Take one down and pass it around, 53 bottles of beer on the wall. | |||
| 53 bottles of beer on the wall, 53 bottles of beer. | |||
| Take one down and pass it around, 52 bottles of beer on the wall. | |||
| 52 bottles of beer on the wall, 52 bottles of beer. | |||
| Take one down and pass it around, 51 bottles of beer on the wall. | |||
| 51 bottles of beer on the wall, 51 bottles of beer. | |||
| Take one down and pass it around, 50 bottles of beer on the wall. | |||
| 50 bottles of beer on the wall, 50 bottles of beer. | |||
| Take one down and pass it around, 49 bottles of beer on the wall. | |||
| 49 bottles of beer on the wall, 49 bottles of beer. | |||
| Take one down and pass it around, 48 bottles of beer on the wall. | |||
| 48 bottles of beer on the wall, 48 bottles of beer. | |||
| Take one down and pass it around, 47 bottles of beer on the wall. | |||
| 47 bottles of beer on the wall, 47 bottles of beer. | |||
| Take one down and pass it around, 46 bottles of beer on the wall. | |||
| 46 bottles of beer on the wall, 46 bottles of beer. | |||
| Take one down and pass it around, 45 bottles of beer on the wall. | |||
| 45 bottles of beer on the wall, 45 bottles of beer. | |||
| Take one down and pass it around, 44 bottles of beer on the wall. | |||
| 44 bottles of beer on the wall, 44 bottles of beer. | |||
| Take one down and pass it around, 43 bottles of beer on the wall. | |||
| 43 bottles of beer on the wall, 43 bottles of beer. | |||
| Take one down and pass it around, 42 bottles of beer on the wall. | |||
| 42 bottles of beer on the wall, 42 bottles of beer. | |||
| Take one down and pass it around, 41 bottles of beer on the wall. | |||
| 41 bottles of beer on the wall, 41 bottles of beer. | |||
| Take one down and pass it around, 40 bottles of beer on the wall. | |||
| 40 bottles of beer on the wall, 40 bottles of beer. | |||
| Take one down and pass it around, 39 bottles of beer on the wall. | |||
| 39 bottles of beer on the wall, 39 bottles of beer. | |||
| Take one down and pass it around, 38 bottles of beer on the wall. | |||
| 38 bottles of beer on the wall, 38 bottles of beer. | |||
| Take one down and pass it around, 37 bottles of beer on the wall. | |||
| 37 bottles of beer on the wall, 37 bottles of beer. | |||
| Take one down and pass it around, 36 bottles of beer on the wall. | |||
| 36 bottles of beer on the wall, 36 bottles of beer. | |||
| Take one down and pass it around, 35 bottles of beer on the wall. | |||
| 35 bottles of beer on the wall, 35 bottles of beer. | |||
| Take one down and pass it around, 34 bottles of beer on the wall. | |||
| 34 bottles of beer on the wall, 34 bottles of beer. | |||
| Take one down and pass it around, 33 bottles of beer on the wall. | |||
| 33 bottles of beer on the wall, 33 bottles of beer. | |||
| Take one down and pass it around, 32 bottles of beer on the wall. | |||
| 32 bottles of beer on the wall, 32 bottles of beer. | |||
| Take one down and pass it around, 31 bottles of beer on the wall. | |||
| 31 bottles of beer on the wall, 31 bottles of beer. | |||
| Take one down and pass it around, 30 bottles of beer on the wall. | |||
| 30 bottles of beer on the wall, 30 bottles of beer. | |||
| Take one down and pass it around, 29 bottles of beer on the wall. | |||
| 29 bottles of beer on the wall, 29 bottles of beer. | |||
| Take one down and pass it around, 28 bottles of beer on the wall. | |||
| 28 bottles of beer on the wall, 28 bottles of beer. | |||
| Take one down and pass it around, 27 bottles of beer on the wall. | |||
| 27 bottles of beer on the wall, 27 bottles of beer. | |||
| Take one down and pass it around, 26 bottles of beer on the wall. | |||
| 26 bottles of beer on the wall, 26 bottles of beer. | |||
| Take one down and pass it around, 25 bottles of beer on the wall. | |||
| 25 bottles of beer on the wall, 25 bottles of beer. | |||
| Take one down and pass it around, 24 bottles of beer on the wall. | |||
| 24 bottles of beer on the wall, 24 bottles of beer. | |||
| Take one down and pass it around, 23 bottles of beer on the wall. | |||
| 23 bottles of beer on the wall, 23 bottles of beer. | |||
| Take one down and pass it around, 22 bottles of beer on the wall. | |||
| 22 bottles of beer on the wall, 22 bottles of beer. | |||
| Take one down and pass it around, 21 bottles of beer on the wall. | |||
| 21 bottles of beer on the wall, 21 bottles of beer. | |||
| Take one down and pass it around, 20 bottles of beer on the wall. | |||
| 20 bottles of beer on the wall, 20 bottles of beer. | |||
| Take one down and pass it around, 19 bottles of beer on the wall. | |||
| 19 bottles of beer on the wall, 19 bottles of beer. | |||
| Take one down and pass it around, 18 bottles of beer on the wall. | |||
| 18 bottles of beer on the wall, 18 bottles of beer. | |||
| Take one down and pass it around, 17 bottles of beer on the wall. | |||
| 17 bottles of beer on the wall, 17 bottles of beer. | |||
| Take one down and pass it around, 16 bottles of beer on the wall. | |||
| 16 bottles of beer on the wall, 16 bottles of beer. | |||
| Take one down and pass it around, 15 bottles of beer on the wall. | |||
| 15 bottles of beer on the wall, 15 bottles of beer. | |||
| Take one down and pass it around, 14 bottles of beer on the wall. | |||
| 14 bottles of beer on the wall, 14 bottles of beer. | |||
| Take one down and pass it around, 13 bottles of beer on the wall. | |||
| 13 bottles of beer on the wall, 13 bottles of beer. | |||
| Take one down and pass it around, 12 bottles of beer on the wall. | |||
| 12 bottles of beer on the wall, 12 bottles of beer. | |||
| Take one down and pass it around, 11 bottles of beer on the wall. | |||
| 11 bottles of beer on the wall, 11 bottles of beer. | |||
| Take one down and pass it around, 10 bottles of beer on the wall. | |||
| 10 bottles of beer on the wall, 10 bottles of beer. | |||
| Take one down and pass it around, 9 bottles of beer on the wall. | |||
| 9 bottles of beer on the wall, 9 bottles of beer. | |||
| Take one down and pass it around, 8 bottles of beer on the wall. | |||
| 8 bottles of beer on the wall, 8 bottles of beer. | |||
| Take one down and pass it around, 7 bottles of beer on the wall. | |||
| 7 bottles of beer on the wall, 7 bottles of beer. | |||
| Take one down and pass it around, 6 bottles of beer on the wall. | |||
| 6 bottles of beer on the wall, 6 bottles of beer. | |||
| Take one down and pass it around, 5 bottles of beer on the wall. | |||
| 5 bottles of beer on the wall, 5 bottles of beer. | |||
| Take one down and pass it around, 4 bottles of beer on the wall. | |||
| 4 bottles of beer on the wall, 4 bottles of beer. | |||
| Take one down and pass it around, 3 bottles of beer on the wall. | |||
| 3 bottles of beer on the wall, 3 bottles of beer. | |||
| Take one down and pass it around, 2 bottles of beer on the wall. | |||
| 2 bottles of beer on the wall, 2 bottles of beer. | |||
| Take one down and pass it around, 1 bottle of beer on the wall. | |||
| 1 bottle of beer on the wall, 1 bottle of beer. | |||
| Take it down and pass it around, no more bottles of beer on the wall. | |||
| No more bottles of beer on the wall, no more bottles of beer. | |||
| Go to the store and buy some more, 99 bottles of beer on the wall. | |||
| ``` | |||
| ## For bonus points | |||
| Did you get the tests passing and the code clean? If you want to, these | |||
| are some additional things you could try: | |||
| * Remove as much duplication as you possibly can. | |||
| * Optimize for readability, even if it means introducing duplication. | |||
| * If you've removed all the duplication, do you have a lot of | |||
| conditionals? Try replacing the conditionals with polymorphism, if it | |||
| applies in this language. How readable is it? | |||
| Then please share your thoughts in a comment on the submission. Did this | |||
| experiment make the code better? Worse? Did you learn anything from it? | |||
| ## Hints | |||
| - Try to capture the structure of the song in your code, where you build up the song by composing its parts. | |||
| ## Running the tests | |||
| To run the tests, run the command `dotnet test` from within the exercise directory. | |||
| ## Autoformatting the code | |||
| F# source code can be formatted with the [Fantomas](https://github.com/fsprojects/fantomas) tool. | |||
| After installing it with `dotnet tool restore`, run `dotnet fantomas .` to format code within the current directory. | |||
| ## Further information | |||
| For more detailed information about the F# track, including how to get help if | |||
| you're having trouble, please visit the exercism.io [F# language page](http://exercism.io/languages/fsharp/resources). | |||
| ## Source | |||
| Learn to Program by Chris Pine [http://pine.fm/LearnToProgram/?Chapter=06](http://pine.fm/LearnToProgram/?Chapter=06) | |||
| @@ -0,0 +1,9 @@ | |||
| module HighScores | |||
| let scores (values: int list): int list = values | |||
| let latest (values: int list): int = List.last values | |||
| let personalBest (values: int list): int = List.max values | |||
| let personalTopThree (values: int list): int list = List.sortDescending values |> List.take (min 3 (List.length values)) | |||
| @@ -0,0 +1,21 @@ | |||
| <Project Sdk="Microsoft.NET.Sdk"> | |||
| <PropertyGroup> | |||
| <TargetFramework>netcoreapp3.0</TargetFramework> | |||
| <IsPackable>false</IsPackable> | |||
| </PropertyGroup> | |||
| <ItemGroup> | |||
| <Compile Include="HighScores.fs" /> | |||
| <Compile Include="HighScoresTests.fs" /> | |||
| </ItemGroup> | |||
| <ItemGroup> | |||
| <PackageReference Include="Microsoft.NET.Test.Sdk" Version="16.6.1" /> | |||
| <PackageReference Include="xunit" Version="2.4.1" /> | |||
| <PackageReference Include="xunit.runner.visualstudio" Version="2.4.1" /> | |||
| <PackageReference Include="FsUnit.xUnit" Version="3.8.1" /> | |||
| </ItemGroup> | |||
| </Project> | |||
| @@ -0,0 +1,41 @@ | |||
| // This file was auto-generated based on version 4.0.0 of the canonical data. | |||
| module HighScoresTests | |||
| open FsUnit.Xunit | |||
| open Xunit | |||
| open HighScores | |||
| [<Fact>] | |||
| let ``List of scores`` () = | |||
| scores [30; 50; 20; 70] |> should equal [30; 50; 20; 70] | |||
| [<Fact>] | |||
| let ``Latest score`` () = | |||
| latest [100; 0; 90; 30] |> should equal 30 | |||
| [<Fact>] | |||
| let ``Personal best`` () = | |||
| personalBest [40; 100; 70] |> should equal 100 | |||
| [<Fact>] | |||
| let ``Personal top three from a list of scores`` () = | |||
| personalTopThree [10; 30; 90; 30; 100; 20; 10; 0; 30; 40; 40; 70; 70] |> should equal [100; 90; 70] | |||
| [<Fact>] | |||
| let ``Personal top highest to lowest`` () = | |||
| personalTopThree [20; 10; 30] |> should equal [30; 20; 10] | |||
| [<Fact>] | |||
| let ``Personal top when there is a tie`` () = | |||
| personalTopThree [40; 20; 40; 30] |> should equal [40; 40; 30] | |||
| [<Fact>] | |||
| let ``Personal top when there are less than 3`` () = | |||
| personalTopThree [30; 70] |> should equal [70; 30] | |||
| [<Fact>] | |||
| let ``Personal top when there is only one`` () = | |||
| personalTopThree [40] |> should equal [40] | |||
| @@ -0,0 +1,25 @@ | |||
| # High Scores | |||
| Manage a game player's High Score list. | |||
| Your task is to build a high-score component of the classic Frogger game, one of the highest selling and addictive games of all time, and a classic of the arcade era. Your task is to write methods that return the highest score from the list, the last added score and the three highest scores. | |||
| ## Running the tests | |||
| To run the tests, run the command `dotnet test` from within the exercise directory. | |||
| ## Autoformatting the code | |||
| F# source code can be formatted with the [Fantomas](https://github.com/fsprojects/fantomas) tool. | |||
| After installing it with `dotnet tool restore`, run `dotnet fantomas .` to format code within the current directory. | |||
| ## Further information | |||
| For more detailed information about the F# track, including how to get help if | |||
| you're having trouble, please visit the exercism.io [F# language page](http://exercism.io/languages/fsharp/resources). | |||
| ## Source | |||
| Tribute to the eighties' arcade game Frogger | |||
| @@ -0,0 +1,60 @@ | |||
| # Scrabble Score | |||
| Given a word, compute the Scrabble score for that word. | |||
| ## Letter Values | |||
| You'll need these: | |||
| ```text | |||
| Letter Value | |||
| A, E, I, O, U, L, N, R, S, T 1 | |||
| D, G 2 | |||
| B, C, M, P 3 | |||
| F, H, V, W, Y 4 | |||
| K 5 | |||
| J, X 8 | |||
| Q, Z 10 | |||
| ``` | |||
| ## Examples | |||
| "cabbage" should be scored as worth 14 points: | |||
| - 3 points for C | |||
| - 1 point for A, twice | |||
| - 3 points for B, twice | |||
| - 2 points for G | |||
| - 1 point for E | |||
| And to total: | |||
| - `3 + 2*1 + 2*3 + 2 + 1` | |||
| - = `3 + 2 + 6 + 3` | |||
| - = `5 + 9` | |||
| - = 14 | |||
| ## Extensions | |||
| - You can play a double or a triple letter. | |||
| - You can play a double or a triple word. | |||
| ## Running the tests | |||
| To run the tests, run the command `dotnet test` from within the exercise directory. | |||
| ## Autoformatting the code | |||
| F# source code can be formatted with the [Fantomas](https://github.com/fsprojects/fantomas) tool. | |||
| After installing it with `dotnet tool restore`, run `dotnet fantomas .` to format code within the current directory. | |||
| ## Further information | |||
| For more detailed information about the F# track, including how to get help if | |||
| you're having trouble, please visit the exercism.io [F# language page](http://exercism.io/languages/fsharp/resources). | |||
| ## Source | |||
| Inspired by the Extreme Startup game [https://github.com/rchatley/extreme_startup](https://github.com/rchatley/extreme_startup) | |||
| @@ -0,0 +1,29 @@ | |||
| module ScrabbleScore | |||
| open System | |||
| let onePointLetter = | |||
| [ 'A' | |||
| 'E' | |||
| 'I' | |||
| 'O' | |||
| 'U' | |||
| 'L' | |||
| 'N' | |||
| 'R' | |||
| 'S' | |||
| 'T' ] | |||
| let score word = | |||
| word | |||
| |> Seq.fold (fun a i -> | |||
| let inset = List.contains (Char.ToUpper i) | |||
| match Char.ToUpper i with | |||
| | _ when inset onePointLetter -> a + 1 | |||
| | _ when inset [ 'D'; 'G' ] -> a + 2 | |||
| | _ when inset [ 'B'; 'C'; 'M'; 'P' ] -> a + 3 | |||
| | _ when inset [ 'F'; 'H'; 'V'; 'W'; 'Y' ] -> a + 4 | |||
| | _ when inset [ 'K' ] -> a + 5 | |||
| | _ when inset [ 'J'; 'X' ] -> a + 8 | |||
| | _ when inset [ 'Q'; 'Z' ] -> a + 10 | |||
| | _ -> a + 0) 0 | |||
| @@ -0,0 +1,21 @@ | |||
| <Project Sdk="Microsoft.NET.Sdk"> | |||
| <PropertyGroup> | |||
| <TargetFramework>netcoreapp3.0</TargetFramework> | |||
| <IsPackable>false</IsPackable> | |||
| </PropertyGroup> | |||
| <ItemGroup> | |||
| <Compile Include="ScrabbleScore.fs" /> | |||
| <Compile Include="ScrabbleScoreTests.fs" /> | |||
| </ItemGroup> | |||
| <ItemGroup> | |||
| <PackageReference Include="Microsoft.NET.Test.Sdk" Version="16.6.1" /> | |||
| <PackageReference Include="xunit" Version="2.4.1" /> | |||
| <PackageReference Include="xunit.runner.visualstudio" Version="2.4.1" /> | |||
| <PackageReference Include="FsUnit.xUnit" Version="3.8.1" /> | |||
| </ItemGroup> | |||
| </Project> | |||
| @@ -0,0 +1,53 @@ | |||
| // This file was auto-generated based on version 1.1.0 of the canonical data. | |||
| module ScrabbleScoreTests | |||
| open FsUnit.Xunit | |||
| open Xunit | |||
| open ScrabbleScore | |||
| [<Fact>] | |||
| let ``Lowercase letter`` () = | |||
| score "a" |> should equal 1 | |||
| [<Fact>] | |||
| let ``Uppercase letter`` () = | |||
| score "A" |> should equal 1 | |||
| [<Fact>] | |||
| let ``Valuable letter`` () = | |||
| score "f" |> should equal 4 | |||
| [<Fact>] | |||
| let ``Short word`` () = | |||
| score "at" |> should equal 2 | |||
| [<Fact>] | |||
| let ``Short, valuable word`` () = | |||
| score "zoo" |> should equal 12 | |||
| [<Fact>] | |||
| let ``Medium word`` () = | |||
| score "street" |> should equal 6 | |||
| [<Fact>] | |||
| let ``Medium, valuable word`` () = | |||
| score "quirky" |> should equal 22 | |||
| [<Fact>] | |||
| let ``Long, mixed-case word`` () = | |||
| score "OxyphenButazone" |> should equal 41 | |||
| [<Fact>] | |||
| let ``English-like word`` () = | |||
| score "pinata" |> should equal 8 | |||
| [<Fact>] | |||
| let ``Empty input`` () = | |||
| score "" |> should equal 0 | |||
| [<Fact>] | |||
| let ``Entire alphabet available`` () = | |||
| score "abcdefghijklmnopqrstuvwxyz" |> should equal 87 | |||