ベストアンサー
最初の方法
= UNICHAR(8730)は、MicrosoftExcelで平方根記号を示します。
Excel2016でテスト済み
2番目の方法
- [挿入]タブに移動をクリックし、シンボルグループからシンボルをクリックします。
- [記号]で[サブセット]から[数学演算子]を選択し、平方根記号を使用します。
回答
最新のCPUのほとんどは、平方根演算をネイティブに提供します。したがって、典型的な最新のハードウェア上の典型的なプログラミング言語では、それが最終的に操作されることはほぼ確実です。
では、ほとんどすべての最新の汎用CPUが使用する方法について説明しましょう。
数値表現
最初に理解する必要があるのは、コンピューターが実際に話している種類の数値をどのように表現するかです。それらは一種の科学的記数法で保存されます。
これで、-134.5のような数値が-1.345 \ times 10 ^ {2}として表されるおなじみの種類の科学的記数法です。
ゼロ以外の数値は、この形式で表すことができます。この形式は、概念的に3つの部分で構成されます。記号(つまり、数値です。正または負)、 mantissa (1から10までの数値、1を含むが10を含まない、この場合は1.345)、および指数(基数が累乗される累乗、この場合は2。指数は一般に負またはゼロである可能性があることに注意してください)。
表現数値が10進数ではなくバイナリ表現を使用して格納されることを除いて、最近のほとんどすべてのコンピューターが使用するものは非常に似ています。したがって、符号ビットとゼロを無視すると(ゼロの平方根を見つけるのは簡単であり、負の数の平方根は実数ではないため)、正の数は実際にはm \ times 2 ^ {e}の形式で格納されます。 mは1から2までの数値です(1を含み、2を含まない)。
この表現は、バイナリポイントを移動できる方法から、「浮動小数点」と呼ばれます(指数を調整することで、よく知っているかもしれない小数点です。
これがすべて重要である理由は、CPUが表現を使用して平方根を計算するためです。指数が偶数であると仮定します。次に:
\ sqrt {m \ times 2 ^ {2 \ epsilon}} = \ sqrt {m} \ times 2 ^ {\ epsilon}
同様に、指数が奇数の場合:
\ sqrt {m \ times 2 ^ {2 \ epsilon + 1}} = \ sqrt {2} \ sqrt {m} \ times 2 ^ {\ epsilon}
mは[1,2)の範囲にあることに注意してください。これは、任意の数の平方根を計算する問題を、その範囲内の数の平方根を計算する問題に減らしたことを意味します。または、\ sqrt {2}を事前計算したくない場合は、[1,4)の範囲の数値。いずれにせよ、その範囲の数値で適切に動作するメソッドを使用できるようになったため、問題が劇的に単純化されました。
乗算と除算
ここまで進んだので、(他の答えを見た場合)解決策はニュートンラプソン反復法のような方法を使用して平方根を計算することだと思うかもしれません。ルート。 nの平方根を計算するには、初期推定値x\_0を選択し、次のように繰り返します。
x\_ {i + 1} = \ frac {1} {2} \ left(x\_i + \ frac {n} {x\_i } \ right)
この答えは間違っています。まあ、それはあなたに正しい答えを与えるという点で間違っていません。しかし、自尊心のあるCPU設計者(またはソフトウェアで実装する必要がある場合はライブラリ作成者)がこの方法で浮動小数点平方根を実装しないという点で間違っています。
2で割るのは非常に安価です。バイナリでの操作(これはベース2であるため、バイナリポイントを1桁シフトするだけです)。ただし、他の除算は非常にコストのかかる操作であり、この場合、操作を複数回実行する必要があります。
除算は非常にコストがかかるため、最近のCPUは同様の反復アルゴリズムを使用します。除算を実行するためのニュートン-ラフソン反復法(実際にはそうではありません)!明らかに、これをハードウェアの内部ループで実行したくない
最近のコンピューターハードウェアでは、実行する方がはるかに安価です。除算演算よりも乗算演算。理由は説明が少し複雑です。これは、以前よりもはるかに多くのトランジスタをチップに取り付けることができるという事実と関係があり、乗算は、多くのトランジスタに効率的に移動できるという問題です。詳細に興味がある場合は、ウォレスの木を検索してください。
とにかく、ポイントは乗算が比較的安価な操作であるということです。したがって、除算ではなく乗算の観点から平方根演算を実装できる場合は、これが適しています。
ニュートンラプソン、2つを取る
ここで、最初の重要な洞察が得られます。平方根を計算する代わりに、平方根の逆数を計算します。つまり、\ sqrt {n}の代わりに、\ frac {1} {\ sqrt {n}}を計算します。これは計算がはるかに簡単な数値であることがわかります。平方根が必要な場合は、この数値にnを掛けると、完了です。
逆数平方根のニュートンラプソン法は次のようになります。 。 x\_0が\ frac {1} {\ sqrt {n}}の初期推定値である場合は、次のように繰り返します。
x\_ {i + 1} = \ frac {1} {2} x\_i \ left(3- n {x\_i} ^ 2 \ right)
繰り返しになりますが、2で割るのは非常に安価で、他のすべては乗算と加算/減算です。
これは実装するのに最適な方法です。ソフトウェアでそれ。さらに、多くの実際の状況(たとえば、ピタゴラスの定理を使用してベクトルを正規化する)では、平方根で除算する方が平方根を乗算するよりも効率が悪いため、平方根の逆数の方が実際には有用です。ルート。
ただし、これは通常ハードウェアに実装される方法ではありません。
ゴールドシュミットのアルゴリズム
これで、平方根と平方根の逆数を一緒に計算するGoldschmidtのアルゴリズムを見ることができます。
b\_n = b\_0 {のような一連の数値Y\_iを見つけることができれば、b\_0 = nが与えられます。 Y\_0} ^ 2 {Y\_1} ^ 2 \ cdots {Y\_ {n-1}} ^ 2は1に近づき、y\_n = {Y\_0} {Y\_1} \ cdots {Y\_ {n-1}}は\ frac {1}に近づきます{\ sqrt {b\_0}}およびx\_n = b\_0 {Y\_0} {Y\_1} \ cdots {Y\_ {n-1}}は\ sqrt {b\_0}に近づきます。
使用するシリーズは基本的にニュートン-ラプソンの更新手順:
\ begin {align *} b\_i&= b\_ {i-1} {Y\_ {i-1}} ^ 2 \\ Y\_i&= \ frac {1} {2 }(3-b\_i)\ end {align *}
そして次に、平方根を追跡できます。
\ begin {align *} x\_0&= n Y\_0 \\ x\_ {i}&= x\_ {i-1} Y\_i \ end {align *}
そして平方根の逆数:
\ begin {align *} y\_0&= Y\_0 \\ y\_ {i}&= y\_ {i-1} Y\_i \ end {align *}
ただし、x\_iとy\_iを追跡する場合は、b\_i = x\_ {i-1} y\_ {i-1}であることに注意してください。したがって、実際にb\_iを追跡する必要はありません。
\ begin {align *} Y\_i&= \ frac {1} {2} \ left(3-b\_i \ right)\\&= 1 + \ frac {1} {2} \ left(1-b\_i \ right)\\&= 1 + \ frac {1} {2} \ left(1-x\_ {i-1} y\_ {i-1} \ right )\ end {align *}
そして今、Y\_iを追跡する必要もありません:
\ begin {align *} x\_i&= x\_ {i-1} \ left(1 + \ frac {1} {2} \ left(1-x\_ {i-1} y\_ {i-1} \ right)\ right)\\&= x\_ {i-1} + x\_ {i- 1} \ frac {1} {2} \ left(1-x\_ {i-1} y\_ {i-1} \ right)\\ y\_i&= y\_ {i-1} \ left(1 + \ frac {1 } {2} \ left(1-x\_ {i-1} y\_ {i-1} \ right)\ right)\\&= y\_ {i-1} + y\_ {i-1} \ frac {1} { 2} \ left(1-x\_ {i-1} y\_ {i-1} \ right)\ end {align *}
ここには冗長な計算がいくつかありますが、これを削除すると、次のことがわかります。アルゴリズム。 Yを\ frac {1} {\ sqrt {n}}の近似値として指定し、次のように設定します。
\ begin {align *} x\_0&= n Y \\ y\_0&= Y \ end {align * }
次に繰り返します:
\ begin {align *} r\_i&= \ frac {1} {2} \ left(1-x\_i y\_i \ right)\\ x\_ {i +1}&= x\_i + x\_i r\_i \\ y\_ {i + 1}&= y\_i + y\_i r\_i \ end {align *}
2で割るのは安価ですが、それも回避できます。 y\_iの代わりにh\_i = \ frac {1} {2} y\_iを追跡します。これはGoldschmidtのアルゴリズムです。
Yが\ frac {1} {\ sqrt {n}}の近似値であるとします。設定:
\ begin {align *} x\_0&= n Y \\ h\_0&= \ frac {Y} {2} \ end {align *}
次に繰り返します:
\ begin {align *} r\_i&= \ frac {1} {2} -x\_i h\_i \\ x\_ {i + 1}&= x\_i + x\_i r\_i \\ h\_ {i + 1}&= h\_i + h\_i r\_i \ end {align *}
次に、x\_iは\ sqrt {n}に収束し、h\_nは\ frac {1} {2 \ sqrt {n}}に収束します。
これをハードウェアに実装する
これまでのところ順調です。確かに非常に単純なアルゴリズムです。しかし、なぜそれが優れているのでしょうか?
最新のCPUには、最適化された積和演算を実行する高速回路が搭載されていることがよくあります。追加、または略してFMA。以前にウォレスツリーへの参照を調べた場合、FMAが単純な乗算演算とほぼ同じくらい効率的である可能性があることは明らかです。
FMAは最も有用なプリミティブの1つです。たとえば、多項式を評価する必要がある場合:
p(x)= a\_0 + a\_1 x + a\_2 x ^ 2 + \ cdots a\_n x ^ n
ホーナー法を使用できますルール。これは基本的にFMAの集まりです。
\ begin {align *} p\_ {n-1}&= a\_ {n-1} + x a\_n \\ p\_ {n-2}&= a\_ {n-2} + x p\_ {n-1} \\&\ vdots \\ p\_1&= a\_1 + x p\_2 \\ p\_0&= a\_0 + x p\_1 \ end {align *}
Goldschmidtのアルゴリズムの内部ループは、3つのFMAであり、他には何もありません。それが利点である理由です。1種類の回路(おそらく1つの回路のみ。次の2つのFMAは独立しているため、パイプライン処理の恩恵を受けることができることに注意してください)と、すべてを実装するための制御ロジックが必要です。また、これは他の多くの操作で役立つ回路であるため、平方根操作だけで多くのハードウェアを無駄にすることはありません。
パズルの最後から2番目のピースは、適切なイニシャルを取得する方法です。見積もり、そして簡単な答えは、最良の方法はテーブルルックアップを使用することです。適度なサイズのテーブルでも、このような狭い範囲の平方根のみを検索するため、非常に効率的です。
パズルの最後のピースは、完了したことをどのように知るかです。繰り返しますか?そして、その答えは、使用している数値の精度と、初期推定値がどれだけ優れているかを知っているということです。それから、事前に必要な最大反復回数を計算できます。したがって、実際にはそのようにループするのではなく、一定の回数だけ反復を行います。