Variable-precision arithmetic (arbitrary-precision arithmetic)

collapse all in page

## Syntax

`xVpa = vpa(x)`

`xVpa = vpa(x,d)`

## Description

example

`xVpa = vpa(x)`

uses variable-precision arithmetic (arbitrary-precision floating-point numbers) to evaluate each element of the symbolic input `x`

to at least `d`

significant digits, where `d`

is the value of the `digits`

function. The default value of `digits`

is 32.

example

`xVpa = vpa(x,d)`

uses at least `d`

significant digits instead of the value of `digits`

.

## Examples

collapse all

### Evaluate Symbolic Inputs with Variable-Precision Arithmetic

Open Live Script

Evaluate symbolic inputs with variable-precision floating-point arithmetic. By default, `vpa`

calculates values to 32 significant digits.

p = sym(pi);pVpa = vpa(p)

`pVpa =$$3.1415926535897932384626433832795$$`

`syms xa = sym(1/3);f = a*sin(2*p*x);fVpa = vpa(f)`

`fVpa =$$0.33333333333333333333333333333333\hspace{0.17em}\mathrm{sin}\left(6.283185307179586476925286766559\hspace{0.17em}x\right)$$`

Evaluate elements of vectors or matrices with variable-precision arithmetic.

V = [x/p a^3];VVpa = vpa(V)

`VVpa =$$\left(\begin{array}{cc}0.31830988618379067153776752674503\hspace{0.17em}x& 0.037037037037037037037037037037037\end{array}\right)$$`

M = [sin(p) cos(p/5); exp(p*x) x/log(p)];MVpa = vpa(M)

MVpa =$$\left(\begin{array}{cc}0& 0.80901699437494742410229341718282\\ {\mathrm{e}}^{3.1415926535897932384626433832795\hspace{0.17em}x}& 0.87356852683023186835397746476334\hspace{0.17em}x\end{array}\right)$$

### Change Precision Used by `vpa`

Open Live Script

By default, `vpa`

evaluates inputs to 32 significant digits. You can change the number of significant digits by using the `digits`

function.

Approximate the expression `100001/10001`

with seven significant digits using `digits`

. Save the old value of `digits`

returned by `digits(7)`

. The `vpa`

function returns only five significant digits, which can mean the remaining digits are zeros.

digitsOld = digits(7);y = sym(100001)/10001;yVpa = vpa(y)

`yVpa =$$9.9991$$`

Check if the remaining digits are zeros by using a higher precision value of `25`

. The result shows that the remaining digits are in fact zeros that are part of a repeating decimal.

digits(25)yVpa = vpa(y)

`yVpa =$$9.999100089991000899910009$$`

Alternatively, to override `digits`

for a single `vpa`

call, change the precision by specifying the second argument.

Find π to 100 significant digits by specifying the second argument.

`pVpa =$$3.141592653589793238462643383279502884197169399375105820974944592307816406286208998628034825342117068$$`

Restore the original precision value in `digitsOld`

for further calculations.

digits(digitsOld)

### Numerically Approximate Symbolic Results

Open Live Script

While symbolic results are exact, they might not be in a convenient form. You can use `vpa`

to numerically approximate exact symbolic results.

Solve a high-degree polynomial for its roots using `solve`

. The `solve`

function cannot symbolically solve the high-degree polynomial and represents the roots using `root`

.

`syms xy = solve(x^4 - x + 1, x)`

y =$$\left(\begin{array}{c}\mathrm{root}\left({z}^{4}-z+1,z,1\right)\\ \mathrm{root}\left({z}^{4}-z+1,z,2\right)\\ \mathrm{root}\left({z}^{4}-z+1,z,3\right)\\ \mathrm{root}\left({z}^{4}-z+1,z,4\right)\end{array}\right)$$

Use `vpa`

to numerically approximate the roots.

yVpa = vpa(y)

yVpa =$$\left(\begin{array}{c}0.72713608449119683997667565867496-0.43001428832971577641651985839602\hspace{0.17em}\mathrm{i}\\ 0.72713608449119683997667565867496+0.43001428832971577641651985839602\hspace{0.17em}\mathrm{i}\\ -0.72713608449119683997667565867496-0.93409928946052943963903028710582\hspace{0.17em}\mathrm{i}\\ -0.72713608449119683997667565867496+0.93409928946052943963903028710582\hspace{0.17em}\mathrm{i}\end{array}\right)$$

`vpa`

Uses Guard Digits to Maintain Precision

Open Live Script

The value of the `digits`

function specifies the minimum number of significant digits used. Internally, `vpa`

can use more digits than `digits`

specifies. These additional digits are called guard digits because they guard against round-off errors in subsequent calculations.

Numerically approximate `1/3`

using four significant digits.

a = vpa(1/3,4)

`a =$$0.3333$$`

Approximate the result `a`

using 20 digits. The result shows that the toolbox internally used more than four digits when computing `a`

. The last digits in the result are incorrect because of the round-off error.

aVpa = vpa(a,20)

`aVpa =$$0.33333333333303016843$$`

### Avoid Hidden Round-Off Errors

Open Live Script

Hidden round-off errors can cause unexpected results.

Evaluate `1/10`

with the default 32-digit precision and then with the 10-digit precision.

a = vpa(1/10,32)

`a =$$0.1$$`

b = vpa(1/10,10)

`b =$$0.1$$`

Superficially, `a`

and `b`

look equal. Check their equality by finding `a - b`

.

roundoff = a - b

`roundoff =$$0.000000000000000000086736173798840354720600815844403$$`

The difference is not equal to zero because `b`

was calculated with only `10`

digits of precision and contains a larger round-off error than `a`

. When you find `a - b`

, `vpa`

approximates `b`

with 32 digits. Demonstrate this behavior.

roundoff = a - vpa(b,32)

`roundoff =$$0.000000000000000000086736173798840354720600815844403$$`

`vpa`

Restores Precision of Common Double-Precision Inputs

Open Live Script

Unlike exact symbolic values, double-precision values inherently contain round-off errors. When you call `vpa`

on a double-precision input, `vpa`

cannot restore the lost precision, even though it returns more digits than the double-precision value. However, `vpa`

can recognize and restore the precision of expressions of the form $\frac{\mathit{p}}{\mathit{q}}$, $\frac{\mathit{p}\pi}{\mathit{q}}$, ${\left(\frac{\mathit{p}}{\mathit{q}}\right)}^{\frac{1}{2}}$, ${2}^{\mathit{q}}$, and ${10}^{\mathit{q}}$, where $\mathit{p}$ and $\mathit{q}$ are modest-sized integers.

First, demonstrate that `vpa`

cannot restore precision for a double-precision input. Call `vpa`

on a double-precision result and the same symbolic result.

dp = log(3);s = log(sym(3));dpVpa = vpa(dp)

`dpVpa =$$1.0986122886681095600636126619065$$`

sVpa = vpa(s)

`sVpa =$$1.0986122886681096913952452369225$$`

d = sVpa - dpVpa

`d =$$0.00000000000000013133163257501600766255995767652$$`

As expected, the double-precision result differs from the exact result at the 16th decimal place.

Demonstrate that `vpa`

restores precision for expressions of the form $\frac{\mathit{p}}{\mathit{q}}$, $\frac{\mathit{p}\pi}{\mathit{q}}$, ${\left(\frac{\mathit{p}}{\mathit{q}}\right)}^{\frac{1}{2}}$, ${2}^{\mathit{q}}$, and ${10}^{\mathit{q}}$, where $\mathit{p}$ and $\mathit{q}$ are modest-sized integers, by finding the difference between the `vpa`

call on the double-precision result and on the exact symbolic result. The differences are $0.0$ showing that `vpa`

restores lost precision for the double-precision input.

d = vpa(1/3) - vpa(1/sym(3))

`d =$$0.0$$`

d = vpa(pi) - vpa(sym(pi))

`d =$$0.0$$`

d = vpa(1/sqrt(2)) - vpa(1/sqrt(sym(2)))

`d =$$0.0$$`

d = vpa(2^66) - vpa(2^sym(66))

`d =$$0.0$$`

d = vpa(10^25) - vpa(10^sym(25))

`d =$$0.0$$`

### Evaluate Symbolic Matrix Variable with Variable-Precision Arithmetic

*Since R2022b*

Open Live Script

Create a symbolic expression `S`

that represents $\mathrm{sin}\left(\left[\begin{array}{cc}\pi & \frac{\pi}{2}\\ \frac{\pi}{2}& \frac{\pi}{3}\end{array}\right]\mathit{X}\right)$, where $\mathit{X}$ is a 2-by-1 symbolic matrix variable.

syms X [2 1] matrixS = sin(hilb(2)*pi*X)

S =$$\begin{array}{l}\mathrm{sin}\left({\Sigma}_{1}\hspace{0.17em}X\right)\\ \\ \mathrm{where}\\ \\ \mathrm{}{\Sigma}_{1}=\left(\begin{array}{cc}\pi & \frac{\pi}{2}\\ \frac{\pi}{2}& \frac{\pi}{3}\end{array}\right)\end{array}$$

Evaluate the expression with variable-precision arithmetic.

SVpa = vpa(S)

SVpa =$$\left(\begin{array}{c}\mathrm{sin}\left(3.1415926535897932384626433832795\hspace{0.17em}{X}_{1}+1.5707963267948966192313216916398\hspace{0.17em}{X}_{2}\right)\\ \mathrm{sin}\left(1.5707963267948966192313216916398\hspace{0.17em}{X}_{1}+1.0471975511965977461542144610932\hspace{0.17em}{X}_{2}\right)\end{array}\right)$$

## Input Arguments

collapse all

`x`

— Input to evaluate

number | vector | matrix | multidimensional array | symbolic number | symbolic vector | symbolic matrix | symbolic multidimensional array | symbolic expression | symbolic function | symbolic character vector | symbolic matrix variable

Input to evaluate, specified as a number, vector, matrix, multidimensional array, or a symbolic number, vector, matrix, multidimensional array, expression, function, character vector, or matrix variable.

`d`

— Number of significant digits

positive integer scalar

Number of significant digits, specified as a positive integer scalar. `d`

must be greater than 1 and less than $${2}^{29}+1$$.

## Output Arguments

collapse all

`xVpa`

— Variable-precision output

symbolic number | symbolic vector | symbolic matrix | symbolic multidimensional array | symbolic expression | symbolic function

Variable-precision output, returned as a symbolic number, vector, matrix, multidimensional array, expression, or function.

For almost all input data types (such as

`sym`

,`symmatrix`

,`double`

,`single`

,`int64`

, and so on),`vpa`

returns the output as data type`sym`

.If the input is a symbolic function of type

`symfun`

, then`vpa`

returns the output as data type`symfun`

. For example,`syms f(x); f(x) = pi*x; g = vpa(f)`

returns the output`g`

as type`symfun`

.If the input is an evaluated symbolic function of type

`sym`

, such as`g = vpa(f(x))`

, then`vpa`

returns the output as data type`sym`

.

## Tips

`vpa`

does not convert fractionsin the exponent to floating point. For example,`vpa(a^sym(2/5))`

returns`a^(2/5)`

.`vpa`

uses more digits than thenumber of digits specified by`digits`

. These extradigits guard against round-off errors in subsequent calculations andare called guard digits.When you call

`vpa`

on a numericinput, such as`1/3`

,`2^(-5)`

,or`sin(pi/4)`

, the numeric expression is evaluatedto a double-precision number that contains round-off errors. Then,`vpa`

iscalled on that double-precision number. For accurate results, convertnumeric expressions to symbolic expressions with`sym`

.For example, to approximate`exp(1)`

, use`vpa(exp(sym(1)))`

.If the second argument d is notan integer,

`vpa`

rounds it to the nearest integerwith`round`

.`vpa`

restores precision for numericinputs that match the forms*p*/*q*,*p*π/*q*, (*p*/*q*)^{1/2}, 2^{q},and 10^{q},where*p*and*q*are modest-sizedintegers.Variable-precision arithmetic is different from IEEE

^{®}Floating-Point Standard 754 in these ways:Inside computations, division by zero throws an error.

The exponent range is larger than in any predefined IEEE mode.

`vpa`

underflows below approximately`10^(-323228496)`

.Denormalized numbers are not implemented.

Zeros are not signed.

The number of

*binary*digits in the mantissa of a result may differ between variable-precision arithmetic and IEEE predefined types.There is only one

`NaN`

representation. No distinction is made between quiet and signaling`NaN`

.No floating-point number exceptions are available.

## Version History

**Introduced before R2006a**

expand all

### R2022b: Evaluate symbolic matrix variables with variable-precision arithmetic

You can evaluate a symbolic matrix variable of type `symmatrix`

with variable-precision arithmetic. The result is a symbolic expression with variable-precision numbers and scalar variables of type `sym`

. For an example, see Evaluate Symbolic Matrix Variable with Variable-Precision Arithmetic.

### R2018a: Support for character vectors has been removed

Support for character vectors that do not define a number has been removed. Instead, first create symbolic numbers and variables using `sym`

and `syms`

, and then use operations on them. For example, use `vpa((1 + sqrt(sym(5)))/2)`

instead of `vpa('(1 + sqrt(5))/2')`

.

## See Also

digits | double | root | vpaintegral

### Topics

- Increase Precision of Numeric Calculations
- Recognize and Avoid Round-Off Errors
- Increase Speed by Reducing Precision
- Choose Numeric or Symbolic Arithmetic
- Change Output Format of Symbolic and Variable-Precision Arithmetic

## MATLAB Command

You clicked a link that corresponds to this MATLAB command:

Run the command by entering it in the MATLAB Command Window. Web browsers do not support MATLAB commands.

Select a Web Site

Choose a web site to get translated content where available and see local events and offers. Based on your location, we recommend that you select: .

You can also select a web site from the following list:

### Americas

- América Latina (Español)
- Canada (English)
- United States (English)

### Europe

- Belgium (English)
- Denmark (English)
- Deutschland (Deutsch)
- España (Español)
- Finland (English)
- France (Français)
- Ireland (English)
- Italia (Italiano)
- Luxembourg (English)

- Netherlands (English)
- Norway (English)
- Österreich (Deutsch)
- Portugal (English)
- Sweden (English)
- Switzerland
- Deutsch
- English
- Français

- United Kingdom (English)

Contact your local office