expr/operator-fraction.go

67 lines
1.3 KiB
Go
Raw Normal View History

// Copyright (c) 2024 Celestino Amoroso (celestino.amoroso@gmail.com).
// All rights reserved.
// operand-fraction.go
package expr
//https://www.youmath.it/lezioni/algebra-elementare/lezioni-di-algebra-e-aritmetica-per-scuole-medie/553-dalle-frazioni-a-numeri-decimali.html
import (
"errors"
"fmt"
)
// -------- fraction term
func newFractionTerm(tk *Token) *term {
return &term{
tk: *tk,
parent: nil,
children: make([]*term, 0, 2),
position: posInfix,
priority: priFraction,
evalFunc: evalFraction,
}
}
// -------- eval func
func evalFraction(ctx ExprContext, self *term) (v any, err error) {
var numValue, denValue any
var num, den int64
var ok bool
if numValue, denValue, err = self.evalInfix(ctx); err != nil {
return
}
if num, ok = numValue.(int64); !ok {
err = fmt.Errorf("numerator must be integer, got %T (%v)", numValue, numValue)
return
}
if den, ok = denValue.(int64); !ok {
err = fmt.Errorf("denominator must be integer, got %T (%v)", denValue, denValue)
return
}
if den == 0 {
err = errors.New("division by zero")
return
}
if den < 0 {
den = -den
num = -num
}
g := gcd(num, den)
num = num / g
den = den / g
if den == 1 {
v = num
} else {
v = &FractionType{num, den}
}
return
}
// init
func init() {
registerTermConstructor(SymVertBar, newFractionTerm)
}