opened
shabbyrobe
username_0
In my application, I need Go OperatingMode to be the default for all calculations. It's very verbose to establish and easy to forget to properly set contexts. Is it possible to add a more convenient way to set the default to be Go?
More convenient way to default to Go OperatingMode?
issue
created
ericlagergren
username_1
I'm not sure. The only "zero-touch" way that would make the default be `Go` would be setting a global variable (like `var DefaultOperatingMode = Go`) that people could modify inside `init()`. But that'd require me to add more runtime checks. I'm not a fan of globals nor of more runtime checks than necessary.

A common format I use when using this library is

```
var ctx = decimal.Big{
    Precision: 19,
    Traps: ^decimal.Condition(0),
    ...
}

// avg sets z to the average of the list, a.
func avg(z, a ...*decimal.Big) *decimal.Big {
    for _, v := range a {
        ctx.Add(z, z, a)
    }
    var n decimal.Big
    return ctx.Quo(z, z, n.SetUint64(uint64(len(a))))
}
```

Or, alternatively, when I don't want to use the `ctx.Add( ... )` form, I'll do something like

```
func d() *decimal.Big {
    return decimal.WithContext(decimal.Context{OperatingMode: Go})
}
foo := d()
...
```
comment
created
shabbyrobe
username_0
Yeah that global was my first thought too, then I started thinking through the horror that could unleash. Being able to modify the behaviour of dependencies that rely in the default being GDA could create some really nasty surprises, which is precisely what I'm trying to avoid! :)

So the main reason why I'm favouring the Go operating mode is that it's about 20% faster (and I'm doing about a jillion calculations so that really 20% really helps), and the other reasons are that the docs say that operations are lossless and because I'd prefer my app blow up on NaN.

So I guess the problem I have is that if I forget even once to do `decimal.WithContext(decimal.Context{OperatingMode: Go})`, I've created a subtle condition where precision could be lost or NaNs could slip through, compromising my whole data pipeline potentially without me knowing.

I'm not sure any of this is right, it's just what I gleaned from reading the docs and code and experimenting with the lib.
comment
created
ericlagergren
username_1
This is a reason why I added methods to `Context`—if you always commit to using the `ctx.Mul( ... )` form you'll be fine. Other libraries require you to use that form, but I like choices so I added both. :-)
comment
created
ericlagergren
username_1
hey, just wondering if you're fine with me closing this issue.
comment
created
ericlagergren
username_1
Feel free to ping me if you've any more questions!
comment
closed
ericlagergren
username_1
issue
created
shabbyrobe
username_0
Sorry for not getting back to you sooner, and thank you for the detailed reply. I'll see how I go with the `ctx.Mul()` form. It could well be enough; as long as it's easy to visually identify wrong use and right use, the way is then paved for writing an automated checker. Would you mind if I commented here again if I run into issues?
comment
created
ericlagergren
username_1
You’re more than welcome to! (Though, if it’s a different question create a separate issue.) My email’s public as well, but I’d kinda prefer to keep things on GitHub if possible so others can benefit from the Q&A.

I like to use the issues as a TODO list of sorts, so I like to close stuff out when I’m finished so I don’t accidentally forget about it.

>
comment