As we discussed above, a floating point number has two limitations 1) the number of digits stored and 2) the maximum exponent used. If we run into numbers that exceed either of these, we can turn to
BigFloat. For example, what if you want to calculate
\(\pi\) to 100 or more digits. See
Chapter 48 for details on how to do this.
To get a floating point number of type
BigFloat, wrap the
big function around a float. For example
x=big(0.25) returns
0.25 and we can verify it’s type with
typeof(x) which returns
BigFloat.
Let’s revisit an example from earlier and sum 1/9 nine times. If we try to turn this into a BigFloat with a=big(1/9), then the result is
0.111111111111111104943205418749130330979824066162109375
This seems to have an accuracy of only 17 digits, which is typical for a 64-bit floating point, so it doesn’t appear to have improved anything. This, like above, is a case of being careful in constructing a
BigFloat. What happens with
big(1/9)? Put on order-of-operations hat and let’s take a look. The
1/9 is done first and since both 1 and 9 are regular integers (
Int64), the result is a
Float64. Then the
big function turns the
Float64 into a
BigFloat, but not we the accuracy expected.
Instead, if we define a=big(1)/big(9), then we get
0.1111111111111111111111111111111111111111111111111111111111111111111111111111109
which looks more like an expected result. To determine the number of digits of accuracy, you can count (painfully) or try
length(string(a)) which will return
81, which is about 5 times the accuracy of
Float64. Technically if you type
precision(a) and this returns 256, which is the number of bits and it has 4 times the binary precision of
Float64 but about 5 times the decimal precision.
Note: looking again at order of operations, the command
length(string(a)) first takes the number
a and returns it as a
String. Then working inside to outside, find the length of the string.
As noted at the beginning of this section, though, if we want to compute \(\pi\) to 1 million decimal digits, what we’ve seen so far only has about 80 digits of accuracy. However, the BigFloat type is quite flexible. The above example used it in its default precision. We can change this with the setprecision function. For example:
setprecision(2^10)
returns 1024, showing that now BigFloats will be stored in this many bits. Such a number will using 16 times the number of binary digits as a Float64. Entering a2=big(1)/big(9) returns
0.111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111
a number that, at a glance, looks to store about 4 times the number of digits as the default BigFloat size. To determine the total number of decimal digits, if we enter
length(string(big(a2)))
returns
311 as the number of decimal digits. This is about 20 times the precision of
Float64.
Subsection 3.4.1 Limitations of BigFloats
Although a
BigFloat stores more digits and allows a wider range of possible numbers, it still has a limitation. Once you create a
BigFloat, it uses the given precision from
setprecision and cannot be changed. So typically, thought needs to be put in before using
setprecision on what the desired level of precision that is needed.
Additionally, operations with
BigFloats are significantly slower that the
Float64 type and unless you need the extra precision, stay with the base type.