// (c) 2020 Aaron Taylor // See LICENSE.txt file for copyright and license details. package main import ( "flag" "fmt" "log" ) // ============================================================================= type surrealUniverse struct { // TODO: Note that the elements of this array are maintained in order // w.r.t. Axiom 2. numbers []surrealNumber nextUniqueID int } func (u *surrealUniverse) exists(num surrealNumber) bool { // TODO: After I implement a LEQ comparison function, the fact that // u.numbers[] is ordered by that comparison will allow me to greatly // shorten the search. for i := 0; i < len(u.numbers); i++ { if num.number == u.numbers[i].number { return true } } return false } func (u *surrealUniverse) cardinality() int { return len(u.numbers) } func (u *surrealUniverse) insert(num surrealNumber) { if !u.exists(num) { num.metadata.identifier = u.nextUniqueID u.nextUniqueID++ // TODO: Need a LEQ function before I can insert in the correct order. // For now, just append to the end. u.numbers = append(u.numbers, num) } } func (u *surrealUniverse) remove(num surrealNumber) { for i := 0; i < len(u.numbers); i++ { if num.number == u.numbers[i].number { u.numbers = append(u.numbers[:i], u.numbers[i+1:]...) } } } // ============================================================================= type surrealNumber struct { number surrealValue metadata surrealMetadata } // TODO: Note that this is split from the metadata so we can do direct // comparisons when numbers are in reduced form. type surrealValue struct { leftSet *surrealSet rightSet *surrealSet } type surrealMetadata struct { identifier int generation int } // ============================================================================= type surrealSet struct { members []surrealNumber } func (s *surrealSet) isMember(num surrealNumber) bool { for i := 0; i < len(s.members); i++ { if num.number == s.members[i].number { return true } } return false } func (s *surrealSet) cardinality() int { return len(s.members) } func (s *surrealSet) insert(num surrealNumber) { if !s.isMember(num) { s.members = append(s.members, num) } } func (s *surrealSet) remove(num surrealNumber) { for i := 0; i < len(s.members); i++ { if num.number == s.members[i].number { s.members[i] = s.members[len(s.members)-1] s.members = s.members[:len(s.members)-1] } } } // ============================================================================= func main() { // Obtain termination conditions from user. remainingGenerations := flag.Int("generations", 2, "Number of generations of surreal numbers to breed.") flag.Parse() if *remainingGenerations < 1 { log.Fatal("ERROR: The argument to '-generations' must be greater than zero.") } // Build a universe to contain all the surreal numbers we breed. // Seed it by hand with the number zero as generation-0. var universe surrealUniverse universe.insert(surrealNumber{surrealValue{nil, nil}, surrealMetadata{0, 0}}) // TODO: Describe the basic algorithm. for generation := 1; generation <= *remainingGenerations; generation++ { // TODO: Continue here next time. // Rough Plan: // allSymbols := buildAllSymbolCombinations(generation) // validNumbers := pruneInvalidSymbolCombinations(allSymbols) // addNumbersToUniverse(validNumbers) } // TODO: These are just for checking progress. How do I want to render the // final generations vs magnitude chart? fmt.Println("Total Numbers:", len(universe.numbers)) fmt.Println(universe.numbers) } // =============================================================================