Compare commits
No commits in common. "main" and "v0.2" have entirely different histories.
24
collatz.go
24
collatz.go
@ -4,32 +4,12 @@ import (
|
|||||||
"collatz/collatz"
|
"collatz/collatz"
|
||||||
"collatz/parsing"
|
"collatz/parsing"
|
||||||
"log"
|
"log"
|
||||||
"strings"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
sequence, err := runCollatz()
|
calculator := collatz.NewCalculator(new(parsing.Cliargs))
|
||||||
|
err := calculator.CalculateCollatz()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatalf("Error calculating Collatz: %v", err)
|
log.Fatalf("Error calculating Collatz: %v", err)
|
||||||
}
|
}
|
||||||
printSequence(sequence)
|
|
||||||
}
|
|
||||||
|
|
||||||
func printSequence(sequence collatz.Sequence) {
|
|
||||||
builder := new(strings.Builder)
|
|
||||||
log.Printf("Collatz sequence with %d iterations:", sequence.Iterations)
|
|
||||||
for i, num := range sequence.Sequence {
|
|
||||||
if i != 0 {
|
|
||||||
builder.WriteString("\n-> ")
|
|
||||||
}
|
|
||||||
builder.WriteString(num.String())
|
|
||||||
}
|
|
||||||
log.Println(builder.String())
|
|
||||||
}
|
|
||||||
|
|
||||||
func runCollatz() (collatz.Sequence, error) {
|
|
||||||
parser := new(parsing.Cliargs)
|
|
||||||
calculator := collatz.NewCalculator(parser)
|
|
||||||
sequence, err := calculator.CalculateCollatz()
|
|
||||||
return sequence, err
|
|
||||||
}
|
}
|
||||||
|
@ -7,55 +7,53 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
type Calculator struct {
|
type Calculator struct {
|
||||||
parser parsing.Parser
|
parser parsing.Parser
|
||||||
three *big.Int
|
three *big.Int
|
||||||
two *big.Int
|
two *big.Int
|
||||||
one *big.Int
|
one *big.Int
|
||||||
sequence Sequence
|
iterations int
|
||||||
}
|
|
||||||
type Sequence struct {
|
|
||||||
Iterations int
|
|
||||||
Sequence []*big.Int
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewCalculator(parser parsing.Parser) *Calculator {
|
func NewCalculator(parser parsing.Parser) *Calculator {
|
||||||
r := &Calculator{
|
r := &Calculator{
|
||||||
parser: parser,
|
parser: parser,
|
||||||
three: big.NewInt(3),
|
three: big.NewInt(3),
|
||||||
two: big.NewInt(2),
|
two: big.NewInt(2),
|
||||||
one: big.NewInt(1),
|
one: big.NewInt(1),
|
||||||
|
iterations: 0,
|
||||||
}
|
}
|
||||||
return r
|
return r
|
||||||
}
|
}
|
||||||
|
|
||||||
func (calc *Calculator) CalculateCollatz() (Sequence, error) {
|
func (o *Calculator) CalculateCollatz() error {
|
||||||
number, err := calc.parser.Parse()
|
number, err := o.parser.Parse()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return Sequence{}, fmt.Errorf("couldn't parse input: %w", err)
|
return fmt.Errorf("couldn't parse input: %w", err)
|
||||||
}
|
}
|
||||||
calc.sequence = Sequence{Iterations: 0}
|
fmt.Print(number.Text(10))
|
||||||
calc.sequence.Sequence = append(calc.sequence.Sequence, new(big.Int).Set(number))
|
err = o.nextNumber(*number)
|
||||||
err = calc.calculateNextCollatzNumber(*number)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return Sequence{}, err
|
return err
|
||||||
}
|
}
|
||||||
return calc.sequence, nil
|
fmt.Println()
|
||||||
|
fmt.Println("Iterations:", o.iterations)
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (calc *Calculator) calculateNextCollatzNumber(in big.Int) error {
|
func (o *Calculator) nextNumber(in big.Int) error {
|
||||||
if in.Cmp(calc.one) < 0 {
|
if in.Cmp(o.one) < 0 {
|
||||||
return fmt.Errorf("must be greater than 0")
|
return fmt.Errorf("must be greater than 0")
|
||||||
}
|
}
|
||||||
if in.Cmp(calc.one) == 0 {
|
if in.Cmp(o.one) == 0 {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
var newNumber *big.Int
|
var newNumber *big.Int
|
||||||
if new(big.Int).And(&in, calc.one).Cmp(calc.one) == 0 {
|
if new(big.Int).And(&in, o.one).Cmp(o.one) == 0 {
|
||||||
newNumber = new(big.Int).Add(new(big.Int).Mul(&in, calc.three), calc.one)
|
newNumber = new(big.Int).Add(new(big.Int).Mul(&in, o.three), o.one)
|
||||||
} else {
|
} else {
|
||||||
newNumber = new(big.Int).Div(&in, calc.two)
|
newNumber = new(big.Int).Div(&in, o.two)
|
||||||
}
|
}
|
||||||
calc.sequence.Iterations++
|
o.iterations++
|
||||||
calc.sequence.Sequence = append(calc.sequence.Sequence, newNumber)
|
fmt.Printf(" -> %s", newNumber.Text(10))
|
||||||
return calc.calculateNextCollatzNumber(*newNumber)
|
return o.nextNumber(*newNumber)
|
||||||
}
|
}
|
||||||
|
@ -38,11 +38,8 @@ func TestCalculateCollatz(t *testing.T) {
|
|||||||
parser := &MockParser{value: big.NewInt(6)}
|
parser := &MockParser{value: big.NewInt(6)}
|
||||||
calculator := NewCalculator(parser)
|
calculator := NewCalculator(parser)
|
||||||
|
|
||||||
sequence, err := calculator.CalculateCollatz()
|
err := calculator.CalculateCollatz()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Errorf("Expected no error, got %v", err)
|
t.Errorf("Expected no error, got %v", err)
|
||||||
}
|
}
|
||||||
if sequence.Iterations != 8 {
|
|
||||||
t.Errorf("Expected 8 iterations, got %v", sequence.Iterations)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
@ -7,6 +7,7 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
type Cliargs struct {
|
type Cliargs struct {
|
||||||
|
value *big.Int
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arg *Cliargs) Parse() (*big.Int, error) {
|
func (arg *Cliargs) Parse() (*big.Int, error) {
|
||||||
@ -18,5 +19,10 @@ func (arg *Cliargs) Parse() (*big.Int, error) {
|
|||||||
if !success {
|
if !success {
|
||||||
return nil, errors.New("argument is not an integer")
|
return nil, errors.New("argument is not an integer")
|
||||||
}
|
}
|
||||||
|
arg.value = num
|
||||||
return num, nil
|
return num, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (arg *Cliargs) GetNumber() *big.Int {
|
||||||
|
return arg.value
|
||||||
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user