4.2 範囲
範囲は、等間隔の要素を持つ行ベクトルを記述する便利な方法です。範囲式は、範囲の最初の要素の値、要素間の増分を表すオプションの値、および範囲の要素が超えない最大値によって定義されます。ベース、増分、および制限は、コロン(':' 文字)で、任意の算術式や関数呼び出しを含めることができます。増分が省略された場合は、1 とみなされます。たとえば、範囲
1 : 5
値のセット[ 1, 2, 3, 4, 5 ]と範囲 を定義します
1 : 3 : 5
値のセットを定義します[ 1, 4 ]。
範囲定数は行ベクトルを指定しますが、Octave は 通常、必要な場合を除き、範囲定数をベクトルに変換しません1 : 10000。これにより、一般的なワークステーションで 80,000 バイトのストレージを使用せずに、次のような定数を記述できます。
範囲をベクトルに変換する必要が生じる一般的な例は、範囲がベクトル内(つまり、角括弧内)に現れる場合です。たとえば、
x = 0 : 0.1 : 1;
xを型の変数として定義しrange、24バイトのメモリを占有する式
y = [ 0 : 0.1 : 1];
y を型として定義しmatrix、88 バイトのメモリを占有します。
このスペース節約の最適化は、関数 optimize_rangeを使用して無効にすることができます。
: val = optimize_range () : old_val = optimize_range (new_val) : old_val = optimize_range (new_val, "local")
範囲の保存に特別なスペース効率の高い形式が使用されるかどうかを照会または設定します。
デフォルト値は true です。このオプションを false に設定すると、Octave は範囲を完全な行列として保存します。
オプションを使用して関数内から呼び出されると"local"、関数とそれが呼び出すサブルーチンの設定がローカルに変更されます。関数を終了すると、元の設定が復元されます。
See also: optimize_diagonal_matrix, optimize_permutation_matrix.
範囲の上限(増分が負の場合は下限)は、必ずしも値のセットに含まれるわけではないことに注意してください。これは、状況によっては役立つことがあります。例:
## x is some predefined range or vector or matrix or array x(1:2:end) += 1; # increment all odd-numbered elements x(2:2:end) -= 1; # decrement all even-numbered elements
上記のコードは、xの要素数が奇数かどうかに関係なく正しく機能するため、2 つのケースを別々に扱う必要はありません。
Octave は、範囲内の値を計算するために浮動小数点演算を使用します。その結果、浮動小数点値で範囲を定義すると、次のような落とし穴に陥る可能性があります。
a = -2 b = (0.3 - 0.2 - 0.1) x = a : b
浮動小数点の丸めにより、b は正確にゼロになる場合とならない場合があります。また、ゼロにならない場合は、ゼロより上または下になる可能性があります。そのため、最終範囲 xには、最終値としてゼロが含まれる場合と含まれない場合があります。同様に、
x = 1.80 : 0.05 : 1.90 y = 1.85 : 0.05 : 1.90
見た目ほど予測可能ではありません。Octave 8.3 の時点では、xには 3 つの要素 (1.80、1.85、1.90) があり、yには 1 つの要素 (1.85 はあるが 1.90 はない) があるという結果が得られました。したがって、範囲で浮動小数点を使用する場合、範囲の開始値を変更すると、上記の例では終了値が変更されていなくても、範囲の終了値に簡単に影響が及ぶ可能性があります。
範囲内の浮動小数点数に関するこのような落とし穴を回避するには、次のいずれかのパターンを使用する必要があります。前のコードに対する変更:
x = (0:2) * 0.05 + 1.80 y = (0:1) * 0.05 + 1.85
により、プラットフォーム、コンパイラ、およびコンパイラ設定間での安全性と再現性がはるかに高まります。要素数がわかっている場合は、linspace関数 ( 「特殊ユーティリティ行列」を参照) を使用することもできます。この関数には、範囲の端点が含まれます。、、、などをうまく使用して、浮動小数点の丸めによる干渉を受けずに制限と増分を設定することもできます round。たとえば、前述の例はfloor、次のいずれかを使用することで、より安全で再現性を高めることができます。 ceilfix
a = -2 b = round ((0.3 - 0.2 - 0.1) * 1e12) / 1e12 # rounds to 12 digits c = floor (0.3 - 0.2 - 0.1) # floors as integer d = floor ((0.3 - 0.2 - 0.1) * 1e12) / 1e12 # floors at 12 digits x = a : b y = a : c z = a : d
スカラーを範囲に追加したり、範囲からスカラーを減算したり(または範囲からスカラーを減算したり)、スカラーを掛け合わせたりするとき、Octave は範囲の展開を避け、結果も範囲として保持しようとします。これは、そうすることが安全であると判断できる場合です。たとえば、次のようにします。
a = 2*(1:1e7) - 1;
は と同じ結果を生成します1:2:2e7-1が、1000万要素のベクトルを形成することはありません。
コロン表記で増分としてゼロを使用することは1:0:1許可されていません。範囲の要素の数を決定する際にゼロによる除算が発生するためです。ただし、増分がゼロの範囲(つまり、すべての要素が等しい)は、特にインデックス付けに便利であり、Octave では組み込み関数を使用してそれらを構築できます。範囲は行ベクトルでなければならないため、は範囲を生成しますが、は 生成しない ことonesに注意してください。ones (1, 10)ones (10, 1)
Octave は範囲式を解析するときに、式の要素を調べて、すべてが定数であるかどうかを判断します。定数である場合は、範囲式を単一の範囲定数に置き換えます。