What is the easiest way to get the machine epsilon in Go? What about other aspects of floating point numbers such as precision, min exponent, max exponent, wobble, etc?
I realize that there is the math/const package with the max and min for the different float types (http://golang.org/src/pkg/math/const.go), but no other information.
One reason I would like to know is to verify that I've reached the maximum precision for a given calculation that the machine can do so that I don't quit to early or try longer then needed.
The other is just for curiosity.
Thanks
EDIT:
For the fun I looked up in some notes from school on how to calculate the epsilon manually for fun and here is a rough translation from c++ http://play.golang.org/p/XOXwIdNfsa enjoy
EDIT: comment from below (thanks for a more idiomatic way of finding epsilon):
Use epsilon := math.Nextafter(1, 2) - 1
Playground – Nick Craig-Wood Mar 5 at 8:07
The machine epsilon (in double precision) is eps =2.220446049250313e−016. It is obtained when the number of terms is n =53.
Machine epsilon or machine precision is an upper bound on the relative approximation error due to rounding in floating point arithmetic. This value characterizes computer arithmetic in the field of numerical analysis, and by extension in the subject of computational science.
Machine epsilon (ϵm) is defined as the distance (gap) between 1 and the next largest floating point number. In programming languages these values are typically available as predefined constants. For example, in C, these constants are FLT_EPSILON and DBL_EPSILON and are defined in the float.
Machine precision is the smallest number eps such that the difference between 1 and 1 + eps is nonzero, ie., it is the smallest difference between two numbers that the computer recognizes. On a 32 bit computer, single precision is 2-23 (approximately 10-7) while double precision is 2-52 (approximately10-16) .
It's not defined, I found the issue resolved as "working as intended" on the issue tracker:
https://code.google.com/p/go/issues/detail?id=966
The suggestion seems to be to use math.Nextafter
to derive the value if you need it.
Specifically, the formula is math.Nextafter(1.0,2.0)-1.0
(the second argument can be any number greater than 1.0).
The above works for any binary floating point type (e.g. the Go types you are referring to.)
package main
import "fmt"
func main() {
f32 := float32(7.)/3 - float32(4.)/3 - float32(1.)
fmt.Println(f32)
f64 := float64(7.)/3 - float64(4.)/3 - float64(1.)
fmt.Println(f64)
}
gives:
-1.1920929e-07
2.220446049250313e-16
taking the absolute (unsigned) value of f32 yields the correct machine ε.
Edit: As mentioned below in a comment from SGJ, this would not work on decimal floating point types, but as far as I'm aware they have not been implemented yet in Golang.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With