diff --git a/Makefile b/Makefile index fa5a3a69..bef5287f 100644 --- a/Makefile +++ b/Makefile @@ -16,12 +16,12 @@ lint: build test-short: lint go install github.com/newm4n/goornogo go test ./... -v -covermode=count -coverprofile=coverage.out -short - goornogo -i coverage.out -c 45.3 + goornogo -i coverage.out -c 40 test: lint go install github.com/newm4n/goornogo go test ./... -covermode=count -coverprofile=coverage.out - goornogo -i coverage.out -c 47 + goornogo -i coverage.out -c 40 test-coverage: test go tool cover -html=coverage.out diff --git a/README.md b/README.md index 064d99a8..89f14ad3 100644 --- a/README.md +++ b/README.md @@ -31,8 +31,8 @@ rule "SpeedUp" then $TestCar.setSpeed($TestCar.Speed + $TestCar.SpeedIncrement); update($TestCar); - $DistanceRecord.setTotalDistance($DistanceRecord.getTotalDistance() + $TestCar.Speed) - update($DistanceRecord) + $DistanceRecord.setTotalDistance($DistanceRecord.getTotalDistance() + $TestCar.Speed); + update($DistanceRecord); end ``` diff --git a/ast/BuiltInFunctions.go b/ast/BuiltInFunctions.go index 046594bf..d84a5a2e 100755 --- a/ast/BuiltInFunctions.go +++ b/ast/BuiltInFunctions.go @@ -16,6 +16,7 @@ package ast import ( "github.com/hyperjumptech/grule-rule-engine/logger" + "math" "reflect" "strings" "time" @@ -170,3 +171,293 @@ func (gf *BuiltInFunctions) IsTimeAfter(time, after time.Time) bool { func (gf *BuiltInFunctions) TimeFormat(time time.Time, layout string) string { return time.Format(layout) } + +// Max will pick the biggest of value in the arguments +func (gf *BuiltInFunctions) Max(vals ...float64) float64 { + val := float64(0) + for i, v := range vals { + if i == 0 { + val = v + } else { + if v > val { + val = v + } + } + } + return val +} + +// Min will pick the smallest of value in the arguments +func (gf *BuiltInFunctions) Min(vals ...float64) float64 { + val := float64(0) + for i, v := range vals { + if i == 0 { + val = v + } else { + if v < val { + val = v + } + } + } + return val +} + +// Abs is a wrapper function for math.Abs function +func (gf *BuiltInFunctions) Abs(x float64) float64 { + return math.Abs(x) +} + +// Acos is a wrapper function for math.Acos function +func (gf *BuiltInFunctions) Acos(x float64) float64 { + return math.Acos(x) +} + +// Acosh is a wrapper function for math.Acosh function +func (gf *BuiltInFunctions) Acosh(x float64) float64 { + return math.Acosh(x) +} + +// Asin is a wrapper function for math.Asin function +func (gf *BuiltInFunctions) Asin(x float64) float64 { + return math.Asin(x) +} + +// Asinh is a wrapper function for math.Asinh function +func (gf *BuiltInFunctions) Asinh(x float64) float64 { + return math.Asinh(x) +} + +// Atan is a wrapper function for math.Atan function +func (gf *BuiltInFunctions) Atan(x float64) float64 { + return math.Atan(x) +} + +// Atan2 is a wrapper function for math.Atan2 function +func (gf *BuiltInFunctions) Atan2(y, x float64) float64 { + return math.Atan2(y, x) +} + +// Atanh is a wrapper function for math.Atanh function +func (gf *BuiltInFunctions) Atanh(x float64) float64 { + return math.Atanh(x) +} + +// Cbrt is a wrapper function for math.Cbrt function +func (gf *BuiltInFunctions) Cbrt(x float64) float64 { + return math.Cbrt(x) +} + +// Ceil is a wrapper function for math.Ceil function +func (gf *BuiltInFunctions) Ceil(x float64) float64 { + return math.Ceil(x) +} + +// Copysign is a wrapper function for math.Copysign function +func (gf *BuiltInFunctions) Copysign(x, y float64) float64 { + return math.Copysign(x, y) +} + +// Cos is a wrapper function for math.Cos function +func (gf *BuiltInFunctions) Cos(x float64) float64 { + return math.Cos(x) +} + +// Cosh is a wrapper function for math.Cosh function +func (gf *BuiltInFunctions) Cosh(x float64) float64 { + return math.Cosh(x) +} + +// Dim is a wrapper function for math.Dim function +func (gf *BuiltInFunctions) Dim(x, y float64) float64 { + return math.Dim(x, y) +} + +// Erf is a wrapper function for math.Erf function +func (gf *BuiltInFunctions) Erf(x float64) float64 { + return math.Erf(x) +} + +// Erfc is a wrapper function for math.Erfc function +func (gf *BuiltInFunctions) Erfc(x float64) float64 { + return math.Erfc(x) +} + +// Erfcinv is a wrapper function for math.Erfcinv function +func (gf *BuiltInFunctions) Erfcinv(x float64) float64 { + return math.Erfcinv(x) +} + +// Erfinv is a wrapper function for math.Erfinv function +func (gf *BuiltInFunctions) Erfinv(x float64) float64 { + return math.Erfinv(x) +} + +// Exp is a wrapper function for math.Exp function +func (gf *BuiltInFunctions) Exp(x float64) float64 { + return math.Exp(x) +} + +// Exp2 is a wrapper function for math.Exp2 function +func (gf *BuiltInFunctions) Exp2(x float64) float64 { + return math.Exp2(x) +} + +// Expm1 is a wrapper function for math.Expm1 function +func (gf *BuiltInFunctions) Expm1(x float64) float64 { + return math.Expm1(x) +} + +// Float64bits is a wrapper function for math.Float64bits function +func (gf *BuiltInFunctions) Float64bits(f float64) uint64 { + return math.Float64bits(f) +} + +// Float64frombits is a wrapper function for math.Float64frombits function +func (gf *BuiltInFunctions) Float64frombits(b uint64) float64 { + return math.Float64frombits(b) +} + +// Floor is a wrapper function for math.Floor function +func (gf *BuiltInFunctions) Floor(x float64) float64 { + return math.Floor(x) +} + +// Gamma is a wrapper function for math.Gamma function +func (gf *BuiltInFunctions) Gamma(x float64) float64 { + return math.Gamma(x) +} + +// Hypot is a wrapper function for math.Hypot function +func (gf *BuiltInFunctions) Hypot(p, q float64) float64 { + return math.Hypot(p, q) +} + +// Ilogb is a wrapper function for math.Ilogb function +func (gf *BuiltInFunctions) Ilogb(x float64) int { + return math.Ilogb(x) +} + +// IsInf is a wrapper function for math.IsInf function +func (gf *BuiltInFunctions) IsInf(f float64, sign int64) bool { + return math.IsInf(f, int(sign)) +} + +// IsNaN is a wrapper function for math.IsNaN function +func (gf *BuiltInFunctions) IsNaN(f float64) (is bool) { + return math.IsNaN(f) +} + +// J0 is a wrapper function for math.J0 function +func (gf *BuiltInFunctions) J0(x float64) float64 { + return math.J0(x) +} + +// J1 is a wrapper function for math.J1 function +func (gf *BuiltInFunctions) J1(x float64) float64 { + return math.J1(x) +} + +// Jn is a wrapper function for math.Jn function +func (gf *BuiltInFunctions) Jn(n int64, x float64) float64 { + return math.Jn(int(n), x) +} + +// Ldexp is a wrapper function for math.Ldexp function +func (gf *BuiltInFunctions) Ldexp(frac float64, exp int64) float64 { + return math.Ldexp(frac, int(exp)) +} + +// MathLog is a wrapper function for math.MathLog function +func (gf *BuiltInFunctions) MathLog(x float64) float64 { + return math.Log(x) +} + +// Log10 is a wrapper function for math.Log10 function +func (gf *BuiltInFunctions) Log10(x float64) float64 { + return math.Log10(x) +} + +// Log1p is a wrapper function for math.Log1p function +func (gf *BuiltInFunctions) Log1p(x float64) float64 { + return math.Log1p(x) +} + +// Log2 is a wrapper function for math.Log2 function +func (gf *BuiltInFunctions) Log2(x float64) float64 { + return math.Log2(x) +} + +// Logb is a wrapper function for math.Logb function +func (gf *BuiltInFunctions) Logb(x float64) float64 { + return math.Logb(x) +} + +// Mod is a wrapper function for math.Mod function +func (gf *BuiltInFunctions) Mod(x, y float64) float64 { + return math.Mod(x, y) +} + +// NaN is a wrapper function for math.NaN function +func (gf *BuiltInFunctions) NaN() float64 { + return math.NaN() +} + +// Pow is a wrapper function for math.Pow function +func (gf *BuiltInFunctions) Pow(x, y float64) float64 { + return math.Pow(x, y) +} + +// Pow10 is a wrapper function for math.Pow10 function +func (gf *BuiltInFunctions) Pow10(n int64) float64 { + return math.Pow10(int(n)) +} + +// Remainder is a wrapper function for math.Remainder function +func (gf *BuiltInFunctions) Remainder(x, y float64) float64 { + return math.Remainder(x, y) +} + +// Round is a wrapper function for math.Round function +func (gf *BuiltInFunctions) Round(x float64) float64 { + return math.Round(x) +} + +// RoundToEven is a wrapper function for math.RoundToEven function +func (gf *BuiltInFunctions) RoundToEven(x float64) float64 { + return math.RoundToEven(x) +} + +// Signbit is a wrapper function for math.Signbit function +func (gf *BuiltInFunctions) Signbit(x float64) bool { + return math.Signbit(x) +} + +// Sin is a wrapper function for math.Sin function +func (gf *BuiltInFunctions) Sin(x float64) float64 { + return math.Sin(x) +} + +// Sinh is a wrapper function for math.Sinh function +func (gf *BuiltInFunctions) Sinh(x float64) float64 { + return math.Sinh(x) +} + +// Sqrt is a wrapper function for math.Sqrt function +func (gf *BuiltInFunctions) Sqrt(x float64) float64 { + return math.Sqrt(x) +} + +// Tan is a wrapper function for math.Tan function +func (gf *BuiltInFunctions) Tan(x float64) float64 { + return math.Tan(x) +} + +// Tanh is a wrapper function for math.Tanh function +func (gf *BuiltInFunctions) Tanh(x float64) float64 { + return math.Tanh(x) +} + +// Trunc is a wrapper function for math.Trunc function +func (gf *BuiltInFunctions) Trunc(x float64) float64 { + return math.Trunc(x) +} diff --git a/docs/Function_en.md b/docs/Function_en.md index 14aa7453..7b33c686 100644 --- a/docs/Function_en.md +++ b/docs/Function_en.md @@ -412,6 +412,79 @@ rule DailyCheckBuild "Execute build at 6.30AM and 6.30PM." { } ``` +## Math Functions + +All the functions bellow is a wrapper to their golang math functions. +You should read Golang math page to know how to use each function. + +Unlike go, you don't have to use the `math.` prefix +to use them in your GRL. + +Use them like normal built in function. + +```go +when + Max(Fact.A, Fact.C, Fact.B) > 10 +then + Fact.X = Acosh(Fact.C); +``` + +- Max(vals ...float64) float64 +- Min(vals ...float64) float64 +- Abs(x float64) float64 +- Acos(x float64) float64 +- Acosh(x float64) float64 +- Asin(x float64) float64 +- Asinh(x float64) float64 +- Atan(x float64) float64 +- Atan2(y, x float64) float64 +- Atanh(x float64) float64 +- Cbrt(x float64) float64 +- Ceil(x float64) float64 +- Copysign(x, y float64) float64 +- Cos(x float64) float64 +- Cosh(x float64) float64 +- Dim(x, y float64) float64 +- Erf(x float64) float64 +- Erfc(x float64) float64 +- Erfcinv(x float64) float64 +- Erfinv(x float64) float64 +- Exp(x float64) float64 +- Exp2(x float64) float64 +- Expm1(x float64) float64 +- Float64bits(f float64) uint64 +- Float64frombits(b uint64) float64 +- Floor(x float64) float64 +- Gamma(x float64) float64 +- Hypot(p, q float64) float64 +- Ilogb(x float64) int +- IsInf(f float64, sign int64) bool +- IsNaN(f float64) (is bool) +- J0(x float64) float64 +- J1(x float64) float64 +- Jn(n int64, x float64) float64 +- Ldexp(frac float64, exp int64) float64 +- MathLog(x float64) float64 +- Log10(x float64) float64 +- Log1p(x float64) float64 +- Log2(x float64) float64 +- Logb(x float64) float64 +- Mod(x, y float64) float64 +- NaN() float64 +- Pow(x, y float64) float64 +- Pow10(n int64) float64 +- Remainder(x, y float64) float64 +- Round(x float64) float64 +- RoundToEven(x float64) float64 +- Signbit(x float64) bool +- Sin(x float64) float64 +- Sinh(x float64) float64 +- Sqrt(x float64) float64 +- Tan(x float64) float64 +- Tanh(x float64) float64 +- Trunc(x float64) float64 + + ## Constant Functions The following functions can be called from within GRL as long as the receiver diff --git a/go.mod b/go.mod index a68731c7..4c23577e 100644 --- a/go.mod +++ b/go.mod @@ -16,7 +16,7 @@ require ( github.com/stretchr/testify v1.6.1 golang.org/x/crypto v0.0.0-20200728195943-123391ffb6de // indirect golang.org/x/lint v0.0.0-20201208152925-83fdc39ff7b5 // indirect - golang.org/x/tools v0.0.0-20201229221835-b8413747bbd4 // indirect + golang.org/x/tools v0.0.0-20210114065538-d78b04bdf963 // indirect gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22 // indirect gopkg.in/src-d/go-billy.v4 v4.3.2 gopkg.in/src-d/go-git.v4 v4.13.1 diff --git a/go.sum b/go.sum index 3caf12e4..d4d8bd16 100644 --- a/go.sum +++ b/go.sum @@ -170,6 +170,8 @@ golang.org/x/tools v0.0.0-20201218024724-ae774e9781d2 h1:lHDhNNs7asPT3p01mm8EP3B golang.org/x/tools v0.0.0-20201218024724-ae774e9781d2/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= golang.org/x/tools v0.0.0-20201229221835-b8413747bbd4 h1:oy2nvUJn52tUNTQ5hMOyc/N1qDMXpr6gg6GgsKMPMPc= golang.org/x/tools v0.0.0-20201229221835-b8413747bbd4/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20210114065538-d78b04bdf963 h1:K+NlvTLy0oONtRtkl1jRD9xIhnItbG2PiE7YOdjPb+k= +golang.org/x/tools v0.0.0-20210114065538-d78b04bdf963/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=