162 lines
2.8 KiB
Go
162 lines
2.8 KiB
Go
package main
|
|
|
|
import (
|
|
"bufio"
|
|
"fmt"
|
|
"log"
|
|
"os"
|
|
"strconv"
|
|
"strings"
|
|
)
|
|
|
|
var comps []Component
|
|
var strongest, best Bridge
|
|
|
|
func main() {
|
|
inp := StdinToStrings()
|
|
for i := range inp {
|
|
comps = append(comps, NewComponent(inp[i]))
|
|
}
|
|
|
|
FindStrongest([]Component{NewComponent("0/0")})
|
|
fmt.Println("Strongest:\n", strongest)
|
|
|
|
FindBest([]Component{NewComponent("0/0")})
|
|
fmt.Println("Best:\n", best)
|
|
}
|
|
|
|
// Strongest, regardless of length
|
|
func FindStrongest(bridge Bridge) {
|
|
if bridge.Strength() > strongest.Strength() {
|
|
strongest = bridge
|
|
}
|
|
for i := range comps {
|
|
if comps[i].Has(bridge.Needs()) && !bridge.Has(comps[i]) {
|
|
FindStrongest(append(bridge, comps[i]))
|
|
}
|
|
}
|
|
}
|
|
|
|
// Longest and Strongest
|
|
func FindBest(bridge Bridge) {
|
|
if bridge.Length() > best.Length() {
|
|
best = append([]Component{}, bridge...)
|
|
} else if bridge.Length() == best.Length() {
|
|
if bridge.Strength() > best.Strength() {
|
|
best = bridge
|
|
}
|
|
}
|
|
|
|
for i := range comps {
|
|
if comps[i].Has(bridge.Needs()) && !bridge.Has(comps[i]) {
|
|
FindBest(append(bridge, comps[i]))
|
|
}
|
|
}
|
|
}
|
|
|
|
type Bridge []Component
|
|
|
|
func (b Bridge) Strength() int {
|
|
var ret int
|
|
for _, v := range []Component(b) {
|
|
ret += v.Strength()
|
|
}
|
|
return ret
|
|
}
|
|
|
|
func (b Bridge) Has(c Component) bool {
|
|
for _, v := range []Component(b) {
|
|
if v.Name == c.Name {
|
|
return true
|
|
}
|
|
}
|
|
return false
|
|
}
|
|
|
|
func (b Bridge) Add(c Component) Bridge {
|
|
b = Bridge(append([]Component(b), c))
|
|
return b
|
|
}
|
|
|
|
func (b Bridge) Needs() int {
|
|
t := []Component(b)
|
|
c := t[len(t)-1]
|
|
if len(t) == 1 {
|
|
return c.Other(0)
|
|
}
|
|
c1 := t[len(t)-2]
|
|
|
|
// Find the side of c that doesn't connect with c1
|
|
if c.Has(c1.Side1) {
|
|
return c.Other(c1.Side1)
|
|
}
|
|
return c.Other(c1.Side2)
|
|
}
|
|
|
|
func (b Bridge) Length() int {
|
|
return len([]Component(b))
|
|
}
|
|
|
|
func (b Bridge) String() string {
|
|
ret := "[ "
|
|
for _, v := range []Component(b) {
|
|
ret += v.Name + " "
|
|
}
|
|
return fmt.Sprint(ret+"(", b.Strength(), ";", b.Length(), ") ]")
|
|
}
|
|
|
|
type Component struct {
|
|
Name string
|
|
Side1, Side2 int
|
|
}
|
|
|
|
func NewComponent(in string) Component {
|
|
c := Component{}
|
|
c.Name = in
|
|
pts := strings.Split(in, "/")
|
|
c.Side1 = Atoi(pts[0])
|
|
c.Side2 = Atoi(pts[1])
|
|
return c
|
|
}
|
|
|
|
func (c *Component) Equals(t Component) bool {
|
|
return c.Side1 == t.Side1 && c.Side2 == t.Side2
|
|
}
|
|
|
|
func (c *Component) Strength() int {
|
|
return c.Side1 + c.Side2
|
|
}
|
|
|
|
func (c *Component) Has(v int) bool {
|
|
return c.Side1 == v || c.Side2 == v
|
|
}
|
|
|
|
func (c *Component) Other(v int) int {
|
|
if c.Side1 == v {
|
|
return c.Side2
|
|
}
|
|
return c.Side1
|
|
}
|
|
|
|
func (c *Component) String() string {
|
|
return c.Name
|
|
}
|
|
|
|
func Atoi(i string) int {
|
|
var ret int
|
|
var err error
|
|
if ret, err = strconv.Atoi(i); err != nil {
|
|
log.Fatal("Invalid Atoi")
|
|
}
|
|
return ret
|
|
}
|
|
|
|
func StdinToStrings() []string {
|
|
var input []string
|
|
scanner := bufio.NewScanner(os.Stdin)
|
|
for scanner.Scan() {
|
|
input = append(input, scanner.Text())
|
|
}
|
|
return input
|
|
}
|