みんなの「教えて(疑問・質問)」にみんなで「答える」Q&Aコミュニティ

こんにちはゲストさん。会員登録(無料)して質問・回答してみよう!

解決済みの質問

浮動小数点演算を固定小数点演算へ変換する

あるプログラムの処理を高速化するために浮動小数点数を固定小数点数に変換したいので、皆様の力を貸してください。

以下のようなプログラムがあります。
-------------------------------------------------------------
#define A 0.105

int main(){
double y;
double a,b;
double t1,t2

t1 = A * a;
t2 = t1 * t1;
y = t2 * b;
printf("y = %lf\n",y);
return 0;
}
-------------------------------------------------------------
a,bが入力でそれぞれ0~6000,0~0.004の値を取ることが分かっています。また、yは出力であり許容誤差は3以下となっています。

上記のプログラムを固定小数点数で記述しなおすとどのようになりますか。
各変数の型はshortでお願いします。

投稿日時 - 2009-09-15 01:04:48

QNo.5290800

すぐに回答ほしいです

質問者が選んだベストアンサー

結論から言うと、16ビット整数型演算の範囲ではご希望の「許容誤差は3以下」は実現できないのではないかと思います。
というのは、kを適当な係数として、途中でどうしても (ka)^2 の計算をせざるを得ないからです。(ka)^2 を16ビット整数の範囲に収めるには、符号なしとしてもkaの値は0~255の整数である必要があります。kaの値が256通りしか取れないので、a=5977の場合とa=6000の場合を区別できなくなります。b=0.004のとき、浮動小数点演算のまま本来の値を計算すると
* a=5977 ならば y=1575.45…
* a=6000 ならば y=1587.6
ですから、この2つの場合の結果が同じ値になってしまうということは誤差が3を越えるということです。

ところで、bの値の有効桁数は?
また、結果が負になることはないはずなのに「符号はありで」と書かれているのはどうしてでしょうか?

投稿日時 - 2009-09-15 20:40:07

お礼

回答いただきありがとうございます。
現状では、求めている整数化ができないことができました。

符号ありでお願いしたのは、他のプログラムでも整数化を
おこなう際にも適用できるようなアドバイスを頂きたかったからです。

投稿日時 - 2009-09-17 01:05:14

このQ&Aは役に立ちましたか?

0人が「このQ&Aが役に立った」と投票しています

回答(5)

ANo.4

そうそう, #3 とちょっと関係するんだけど「yは出力であり許容誤差は3以下」ってのがよくわかんないんだよね. この許容誤差が絶対誤差ならそもそも小数部は不要だし.
「固定小数点のフォーマット」といっても特に考えることはなく
・符号は必要か不要か
・小数部に何ビット割り当てるか
を決めるだけです. 表現としては Qn (符号付きで小数部が nビット) という言い方があります.

投稿日時 - 2009-09-15 11:27:40

お礼

解答ありがとうございます。
質問を見直したところ、意図通りの質問ができていなことに気付いたので質問内容を少し訂正させていただきます。

実行時に、浮動小数点演算が発生しないようにプログラムを書き換えたいです。
そのため、t1 = A * aを以下のように書き換えたいです。

  t1 = (short)(a * (short)(A * a_LSB / t1_LSB));

この時の、a_LSB,t1_LSBを求めたいです。
また、入力はA/D変換により整数化されており、変換処理は以下の通りです。。
  a = (short)(a_in / a_LSB);
bについても同様にA/D変換処理を行っています。
そして、a_in,b_inのレンジがそれぞれ0~6000、0~0.004となります。

符号はありでお願いします。

質問内容が少し変わってしまった申し訳ないのですが、
ご教授お願いいたします。

投稿日時 - 2009-09-15 14:28:19

ANo.3

yの誤差が3以下ということはt2の小数部は無視してもいいのかもしれませんね
それならt2は整数のみ、bは少数のみとして整数*小数の演算ですみそうですが

投稿日時 - 2009-09-15 09:09:38

お礼

回答ありがとうございます。
質問が少し間違っていました。

投稿日時 - 2009-09-15 14:29:58

ANo.2

6000で13ビット必要ですよね(1011101110000)
符号なしとしても残り3ビットで小数を扱うのは無理だと思います
変数を32ビットにして最大の整数値が396900(6000*0.105*6000*0.105)として19ビットを整数、
残りを小数にすればどうでしょう

投稿日時 - 2009-09-15 06:59:41

ANo.1

固定小数点のフォーマットは?
t1, t2 の値の範囲は?
「short」の大きさは何ビット?

投稿日時 - 2009-09-15 01:27:01

補足

>固定小数点のフォーマットは?
固定小数点のフォーマットについてよくわからないのですが、どのようなものがあるのでしょうか。
一般的なものがあるのでしたら、それでお願いいたします。

>t1, t2 の値の範囲は?
t1とt2は入力から求めるのですが、それぞれ0~630、0~396900です。

>「short」の大きさは何ビット?
16ビットでお願いします。

投稿日時 - 2009-09-15 02:22:23

あなたにオススメの質問