はじめに
何かしら、大学の論文のタイトル的な感じを受けますが、これが組み込みエンジニアの道です。それでは、いってみましょう。
結論:処理系(実装)によって異なる可能性がある。
C90規格では、整数除算の剰余の符号の扱いは実装定義となっています。つまり、除数または被除数のいずれかが負の数である場合、剰余の符号は処理系によって異なる可能性があります。
具体的には以下の点が重要です:
- C90では、剰余が0でない場合、その符号は不確定です。
- C90では、除数または被除数が負の数の場合、剰余の符号は特に言語仕様で規定されておらず、実装定義(処理系依存)とされています。
- ただし、有効な演算を行うことができた場合、必ず
(a/b)*b + a%b == a
という関係式が成り立つことが保証されています。 - 多くの実装(処理系)では「0への切捨て除算」が使用されており、この場合、余りは被除数と同じ符号になります。
- 一部の実装(処理系)では、オペランドが負の値を持つ場合、”%” 演算子の結果の符号は第1オペランド(被除数)の符号になるという規定を設けています
C90以降のC99やC++11では、この挙動がより厳密に定義されるようになりましたが、C90時点では移植性の観点から注意が必要で、処理系(コンパイラ、インタプリタ)が変わる場合は、違いがないか確認する必要があります。違いがあれば、処理を変更する必要もあります。
0への切捨て除算とは
0への切捨て除算は、整数除算の一種で、商の小数部分を0の方向に切り捨てる方法です。この方法には以下の特徴があります:
- 結果は常に整数となり、小数部分は破棄されます。
- 被除数と除数の符号によって結果が異なります:
- 正の数を正の数で割る場合:通常の切り捨てと同じ結果になります。
- 負の数を正の数で割る場合:0に向かって切り上げられます。
- 正の数を負の数で割る場合:0に向かって切り上げられます。
- 負の数を負の数で割る場合:通常の切り捨てと同じ結果になります。
- この方式では、剰余の符号は被除数と同じになります。
- 多くのプログラミング言語やコンピュータシステムで採用されている方式です。
- C言語では、整数どうしの除算は小数以下切り捨てと定義されており、これは0への切捨て除算に相当します
注意点として、0での除算(ゼロ除算)は定義されておらず、多くのプログラミング環境ではエラーとなります。また、言語や環境によっては異なる除算方式を採用している場合もあるため、使用する際は仕様を確認することが重要です。
0への切捨て除算 使用例
(割られる数) = (割る数) × (商) + (余り)
10 /3の場合 3×-3‐1= -10はなる。
10/-3 の場合 -3×-3+1=10になる。
余りは、被乗数の符号になること
さいごに
今回は前提条件が難しい内容で理解するのが困難でした。この記述の始まりは、MISRA-Cです。使用する処理系定義の動作はすべて文書化しなければならない。という記述があり、もしC90規格の処理系を使う場合は、この整数乗算の剰余の符号については、文書化してプロジェクトを進めないといけないです。C言語の最新の規格は、2011年に制定されましたC11(ISO/IEC 9899:2011)ですが、C90規格の処理系を使う可能性があれば、頭の片隅に入れておくといいということですね。では、
|
コメント