diff --git a/go/current b/go/current deleted file mode 120000 index 4e19c2a..0000000 --- a/go/current +++ /dev/null @@ -1 +0,0 @@ -prime-factors \ No newline at end of file diff --git a/go/nth-prime/README.md b/go/nth-prime/README.md new file mode 100644 index 0000000..c485307 --- /dev/null +++ b/go/nth-prime/README.md @@ -0,0 +1,27 @@ +# Nth Prime + +Write a program that can tell you what the nth prime is. + +By listing the first six prime numbers: 2, 3, 5, 7, 11, and 13, we can see that +the 6th prime is 13. + +If your language provides methods in the standard library to deal with prime +numbers, pretend they don't exist and implement them yourself. + +To run the tests simply run the command `go test` in the exercise directory. + +If the test suite contains benchmarks, you can run these with the `-bench` +flag: + + go test -bench . + +For more detailed info about the Go track see the [help +page](http://exercism.io/languages/go). + +## Source + +A variation on Problem 7 at Project Euler [http://projecteuler.net/problem=7](http://projecteuler.net/problem=7) + +## Submitting Incomplete Problems +It's possible to submit an incomplete solution so you can see how others have completed the exercise. + diff --git a/go/nth-prime/nth_prime.go b/go/nth-prime/nth_prime.go new file mode 100644 index 0000000..9cbea87 --- /dev/null +++ b/go/nth-prime/nth_prime.go @@ -0,0 +1,33 @@ +package prime + +var sieve []int + +func Nth(n int) (int, bool) { + if len(sieve) == 0 { + sieve = append(sieve, 0) + sieve = append(sieve, 2) + } + if n == 0 { + return 0, false + } + + for i := sieve[len(sieve)-1]; n <= len(sieve); i++ { + // Check if i is a prime + isPrime := true + for j := 1; j < len(sieve); j++ { + if i%sieve[j] == 0 { + // Not a prime + isPrime = false + break + } + } + if isPrime { + // Found a new prime + sieve = append(sieve, i) + if len(sieve) >= n { + break + } + } + } + return sieve[n], true +} diff --git a/go/nth-prime/nth_prime_test.go b/go/nth-prime/nth_prime_test.go new file mode 100644 index 0000000..03f23e8 --- /dev/null +++ b/go/nth-prime/nth_prime_test.go @@ -0,0 +1,39 @@ +package prime + +import "testing" + +var tests = []struct { + n int + p int + ok bool +}{ + {1, 2, true}, + {2, 3, true}, + {3, 5, true}, + {4, 7, true}, + {5, 11, true}, + {6, 13, true}, + {10001, 104743, true}, + {0, 0, false}, +} + +func TestNth(t *testing.T) { + for _, test := range tests { + switch p, ok := Nth(test.n); { + case !ok: + if test.ok { + t.Fatalf("Nth(%d) returned !ok. Expecting ok.", test.n) + } + case !test.ok: + t.Fatalf("Nth(%d) = %d, ok = %t. Expecting !ok.", test.n, p, ok) + case p != test.p: + t.Fatalf("Nth(%d) = %d, want %d.", test.n, p, test.p) + } + } +} + +func BenchmarkNth(b *testing.B) { + for i := 0; i < b.N; i++ { + Nth(10001) + } +} diff --git a/go/prime-factors/prime.go b/go/prime-factors/prime.go index 4474b35..feab86d 100644 --- a/go/prime-factors/prime.go +++ b/go/prime-factors/prime.go @@ -1,16 +1,19 @@ package prime -import "fmt" - const testVersion = 2 var sieve []int64 var iter int func Factors(num int64) []int64 { - fmt.Println("Factors Called on ", num) - if num == 1 { + if len(sieve) == 0 { + sieve = append(sieve, int64(2)) + } + switch num { + case 1: return []int64{} + case 2: + return []int64{2} } for i := range sieve { if sieve[i] == num { @@ -22,28 +25,26 @@ func Factors(num int64) []int64 { return append([]int64{sieve[i]}, Factors(div)...) } } + // If we're here, we don't have the prime factors for this number - // Add 1 to the highest prime that we have and find the next prime - i := int64(2) - if len(sieve) > 0 { - i = sieve[len(sieve)-1] - } - fmt.Println(" Looking for a new prime starting at ", i) - for ; i <= num; i++ { + topPrime := sieve[len(sieve)-1] + for i := sieve[0]; i*topPrime <= num; i++ { + // Check if i is a prime isPrime := true for j := range sieve { if i%sieve[j] == 0 { + // Not a prime isPrime = false - } - if !isPrime { break } } if isPrime { + // Found a new prime sieve = append(sieve, i) - // New prime in the sieve, try again + // New data, recurse return Factors(num) } } - return []int64{} + // Is this a prime? + return []int64{num} } diff --git a/go/prime-factors/primefactors_test.go b/go/prime-factors/primefactors_test.go index ec79454..40bbed8 100644 --- a/go/prime-factors/primefactors_test.go +++ b/go/prime-factors/primefactors_test.go @@ -3,7 +3,6 @@ package prime // Return prime factors in increasing order import ( - "fmt" "reflect" "testing" ) @@ -32,13 +31,7 @@ func TestPrimeFactors(t *testing.T) { t.Fatalf("Found testVersion = %v, want %v", testVersion, targetTestVersion) } for _, test := range tests { - fmt.Print("Running Test: ") - fmt.Print(test) - fmt.Print(" :: ") actual := Factors(test.input) - fmt.Print(actual) - fmt.Print(" Sieve: ") - fmt.Println(sieve) if !reflect.DeepEqual(actual, test.expected) { t.Errorf("prime.Factors(%d) = %v; expected %v", test.input, actual, test.expected)