adventofcode/2015/day11/main.go
2016-12-16 16:21:15 -06:00

96 lines
1.5 KiB
Go

package main
import (
"fmt"
"os"
"strings"
)
func printUsage() {
fmt.Println("Usage: day11 <string> [add-amt]")
fmt.Println("If add-amt isn't given, we just add 1")
os.Exit(1)
}
func main() {
args := os.Args
if len(args) < 2 {
printUsage()
}
var orig string
orig = args[1]
var valid bool
for !valid {
orig = addOneToString(orig)
valid = testPassword(orig)
}
fmt.Println(orig)
}
func addOneToString(s string) string {
lastPlace := s[len(s)-1]
ret := s[:len(s)-1]
if lastPlace == 'z' {
lastPlace = 'a'
ret = addOneToString(s[:len(s)-1])
} else {
lastPlace++
}
return ret + string(lastPlace)
}
func testPassword(s string) bool {
if hasValidChars(s) && hasStraight(s) && hasDoubles(s) {
return true
}
return false
}
// Test if string contains only valid chars
func hasValidChars(s string) bool {
if strings.Count(s, "i") > 0 {
return false
}
if strings.Count(s, "o") > 0 {
return false
}
if strings.Count(s, "l") > 0 {
return false
}
return true
}
// Test if string has a 3 char straight
func hasStraight(s string) bool {
for i := range s {
if i > 1 {
if (s[i-2] == s[i]-2) && (s[i-1] == s[i]-1) {
return true
}
}
}
return false
}
// Test if string has 2 doubles
func hasDoubles(s string) bool {
if i := hasDouble(s); i >= 0 {
return (hasDouble(s[i+2:]) >= 0)
}
return false
}
// Returns index of first double in string
// -1 if there isn't one
func hasDouble(s string) int {
for i := range s {
if i > 0 {
if s[i-1] == s[i] {
return i - 1
}
}
}
return -1
}