# artemkorsakov's solution

## to Anagram in the Go Track

Published at Feb 21 2019 · 0 comments
Instructions
Test suite
Solution

Given a word and a list of possible anagrams, select the correct sublist.

Given `"listen"` and a list of candidates like `"enlists" "google" "inlets" "banana"` the program should return a list containing `"inlets"`.

## Running the tests

To run the tests run the command `go test` from within the exercise directory.

If the test suite contains benchmarks, you can run these with the `--bench` and `--benchmem` flags:

``````go test -v --bench . --benchmem
``````

Keep in mind that each reviewer will run benchmarks on a different machine, with different specs, so the results from these benchmark tests may vary.

## Further information

For more detailed information about the Go track, including how to get help if you're having trouble, please visit the exercism.io Go language page.

## Source

Inspired by the Extreme Startup game https://github.com/rchatley/extreme_startup

## Submitting Incomplete Solutions

It's possible to submit an incomplete solution so you can see how others have completed the exercise.

### anagram_test.go

``````package anagram

import (
"fmt"
"sort"
"testing"
)

func equal(a []string, b []string) bool {
if len(b) != len(a) {
return false
}

sort.Strings(a)
sort.Strings(b)
return fmt.Sprintf("%v", a) == fmt.Sprintf("%v", b)
}

func TestDetectAnagrams(t *testing.T) {
for _, tt := range testCases {
actual := Detect(tt.subject, tt.candidates)
if !equal(tt.expected, actual) {
msg := `FAIL: %s
Subject %s
Candidates %q
Expected %q
Got %q
`
t.Fatalf(msg, tt.description, tt.subject, tt.candidates, tt.expected, actual)
} else {
t.Logf("PASS: %s", tt.description)
}
}
}

func BenchmarkDetectAnagrams(b *testing.B) {

for i := 0; i < b.N; i++ {

for _, tt := range testCases {
Detect(tt.subject, tt.candidates)
}

}

}``````

### cases_test.go

``````package anagram

// Source: exercism/problem-specifications
// Commit: baaf092 anagram: words are not anagrams of themselves
// Problem Specifications Version: 1.4.0

var testCases = []struct {
description string
subject     string
candidates  []string
expected    []string
}{
{
description: "no matches",
subject:     "diaper",
candidates: []string{
"hello",
"world",
"zombies",
"pants"},
expected: []string{},
},
{
description: "detects two anagrams",
subject:     "master",
candidates: []string{
"stream",
"pigeon",
"maters"},
expected: []string{
"stream",
"maters"},
},
{
description: "does not detect anagram subsets",
subject:     "good",
candidates: []string{
"dog",
"goody"},
expected: []string{},
},
{
description: "detects anagram",
subject:     "listen",
candidates: []string{
"enlists",
"inlets",
"banana"},
expected: []string{
"inlets"},
},
{
description: "detects three anagrams",
subject:     "allergy",
candidates: []string{
"gallery",
"ballerina",
"regally",
"clergy",
"largely",
expected: []string{
"gallery",
"regally",
"largely"},
},
{
description: "does not detect non-anagrams with identical checksum",
subject:     "mass",
candidates: []string{
"last"},
expected: []string{},
},
{
description: "detects anagrams case-insensitively",
subject:     "Orchestra",
candidates: []string{
"cashregister",
"Carthorse",
expected: []string{
"Carthorse"},
},
{
description: "detects anagrams using case-insensitive subject",
subject:     "Orchestra",
candidates: []string{
"cashregister",
"carthorse",
expected: []string{
"carthorse"},
},
{
description: "detects anagrams using case-insensitive possible matches",
subject:     "orchestra",
candidates: []string{
"cashregister",
"Carthorse",
expected: []string{
"Carthorse"},
},
{
description: "does not detect a anagram if the original word is repeated",
subject:     "go",
candidates: []string{
"go Go GO"},
expected: []string{},
},
{
description: "anagrams must use all letters exactly once",
subject:     "tapper",
candidates: []string{
"patter"},
expected: []string{},
},
{
description: "words are not anagrams of themselves (case-insensitive)",
subject:     "BANANA",
candidates: []string{
"BANANA",
"Banana",
"banana"},
expected: []string{},
},
}``````
``````package anagram

import (
"strings"
)

const alphabet = "abcdefghijklmnopqrstuvwxyz"

// Detect returns anagrams of the given word.
func Detect(subject string, candidates []string) []string {
result := make([]string, 0)
for _, candidate := range candidates {
if IsAnagram(subject, candidate) {
result = append(result, candidate)
}
}
return result
}

// IsAnagram checks whether words are anagrams.
func IsAnagram(first string, second string) bool {
if len(first) != len(second) {
return false
}

firstLower := strings.ToLower(first)
secondLower := strings.ToLower(second)
if firstLower == secondLower {
return false
}

for _, c := range alphabet {
if strings.Count(firstLower, string(c)) != strings.Count(secondLower, string(c)) {
return false
}
}
return true
}``````