数値演算またはシンボリック演算の選択
Symbolic Math Toolbox™ では、数値演算またはシンボリック演算を使用して数字を操作します。数値演算では、倍精度または可変精度による浮動小数点形式で数値を表現します。シンボリック演算では、厳密な形式で数値を表現します。このトピックでは倍精度の演算、可変精度の演算、シンボリック演算を比較します。
倍精度の演算
MATLAB® の数値計算は、既定で倍精度演算を使用します。たとえば、式 10001/1001, π と を評価します。結果は倍精度値に変換されます。
x = 10001/1001 y = pi z = sqrt(2)
x = 9.9910 y = 3.1416 z = 1.4142
倍精度演算の詳細については、浮動小数点数を参照してください。この演算は、Symbolic Math Toolbox を所有していない場合、またはシンボリック入力を受け取らない関数を使用する場合に推奨されます。それ以外の場合は、厳密にシンボリック演算および可変精度の演算が推奨されます。シンボリック値を倍精度値に変換するには、関数 double
を使用します。
可変精度の演算
vpa
を使用した可変精度の演算は、Symbolic Math Toolbox で数値計算を行う場合に推奨される方法です。可変精度の演算で計算を実行する場合、有効桁数を指定できます。
たとえば、vpa
を使用して分数 10001/1001 を評価します。既定では、vpa
は有効桁数 32 桁までの入力を評価します。有効桁数が少なくとも 32 桁になるように分数 10001/1001 を近似します。
vpa(10001/1001)
ans = 9.991008991008991008991008991009
有効桁数が少なくとも 8 桁になるように分数を近似します。関数 digits
を使用して有効桁数を変更します。
digits(8); vpa(10001/1001)
ans = 9.991009
可変精度の演算では、有効桁数を増やして精度を向上させることができます。計算を高速化し、メモリ使用量を減らすために有効桁数を減らすことも有効です。
シンボリック演算
Symbolic Math Toolbox では、関数 sym
および syms
を使用して厳密なシンボリック計算を実行できます。シンボリック演算では、x/2
、2^(1/2)
、pi
などの厳密な形式で数値と変数を含む計算を実行できます。以下の 3 つの例では、シンボリック演算でのさまざまな計算方法を示します。
無理数の表現
sym
を使用してシンボリック数を作成します。無理数 π および をシンボリック形式で表現します。
x = sym(pi) y = sqrt(sym(2))
x = pi y = 2^(1/2)
大きな整数の計算の実行
数値を宣言する場合、MATLAB では数値を倍精度に自動で変換します。たとえば、sym
の入力引数として整数 80435758145817515
を定義します。この数値は、倍精度の最大連続整数 flintmax
(つまり 2^53
) より大きいため、精度が低下します。
Z = 80435758145817515 Zinaccurate = sym(80435758145817515)
Z = 8.0436e+16 Zinaccurate = 80435758145817520
sym
の入力引数として使用します。Zaccurate = sym('80435758145817515')
Zaccurate = 80435758145817515
シンボリック演算を使用すれば、大きな整数の計算を正確に実行できます。たとえば、3 つの大きな整数をそれぞれ 3 乗した和を評価します。
Z1 = sym('80435758145817515') Z2 = sym('12602123297335631') Z3 = sym('-80538738812075974') Zsum = Z1^3 + Z2^3 + Z3^3
Z1 = 80435758145817515 Z2 = 12602123297335631 Z3 = -80538738812075974 Zsum = 42
数学の方程式の求解
シンボリック演算を使用して、数学の方程式を解くことができます。たとえば、2 次方程式 ax2 + bx + c = 0 を解きます。syms
を使用して、2 次方程式の変数 x と係数 a、b、c を宣言します。
syms a b c x eqn = a*x^2 + b*x + c == 0;
solve
を使用して解を求め、シンボリック式としてそれを返します。
sols = solve(eqn,x)
sols = -(b + (b^2 - 4*a*c)^(1/2))/(2*a) -(b - (b^2 - 4*a*c)^(1/2))/(2*a)
subs
を使用して係数にシンボリック値を代入します。a = 1, b = 2, および c = 3 とします。2 次方程式の解をシンボリック数として返します。
solsSym = subs(sols,[a b c],[1 2 3])
solsSym = - (8^(1/2)*1i)/2 - 1 (8^(1/2)*1i)/2 - 1
その後、シンボリック解を倍精度または可変精度の浮動小数点形式に変換できます。
digits(32); solsDouble = double(solsSym) solsVpa = vpa(solsSym)
solsDouble = -1.0000 - 1.4142i -1.0000 + 1.4142i solsVpa = - 1.0 - 1.4142135623730950488016887242097i - 1.0 + 1.4142135623730950488016887242097i
数値演算とシンボリック演算の比較
以下の表は倍精度の演算、可変精度の演算、シンボリック演算の比較です。
倍精度 | 可変精度 | シンボリック | |
---|---|---|---|
例 1: sin(π) の評価 | a = pi sin(pi) a = 3.1416 ans = 1.2246e-16 | b = vpa(pi) sin(b) b = 3.1415926535897932384626433832795 ans = -3.2101083013100396069547145883568e-40 | c = sym(pi) sin(c) c = pi ans = 0 |
例 2: 1 - 3*(4/3 - 1) の評価 | a = 4/3 1 - 3*(a - 1) a = 1.3333 ans = 2.2204e-16 | digits(16); b = vpa(4/3) 1 - 3*(b - 1) b = 1.333333333333333 ans = 3.308722450212111e-24 | c = sym(4)/3 1 - 3*(c - 1) c = 4/3 ans = 0 |
使用した関数 | double | vpa digits | sym |
データ型 | double | sym | sym |
丸め誤差 | あり。解は 16 桁の精度がある | あり。桁数は使用した精度に左右される | なし。結果は厳密 |
速度 | 高速 | 高速。使用した精度に左右される | 最も低速 |
メモリ使用量 | 最小 | 可変。使用した精度に左右される | 最大 |