11

[0、1]の範囲の浮動小数点数があり、それを量子化して符号なしバイトに格納したいとします。当たり前のように聞こえますが、実際には非常に複雑です。

明らかな解決策は次のようになります。

unsigned char QuantizeFloat(float a)
{
  return (unsigned char)(a * 255.0f);
}

これは、0から255までのすべての数値を取得するまでは機能しますが、整数の分布は均一ではありません。この関数は255、aが正確にである場合にのみ戻ります1.0f。良い解決策ではありません。

適切な丸めを行うと、問題がシフトします。

unsigned char QuantizeFloat(float a)
{
  return (unsigned char)(a * 255.0f + 0.5f);
}

ここでは、結果0は他のどの数値よりもフロート範囲の半分しかカバーしていません。

浮動小数点範囲を均等に分散して量子化するにはどうすればよいですか?理想的には、均等に分散されたランダムフロートを量子化する場合、整数の均等な分布を取得したいと思います。

何か案は?


ところで:また、私のコードはCにあり、問題は言語に依存しません。C以外の人の場合:変換することでフロートが切り捨てられると仮定しfloatます。int

編集:ここで混乱があったので:最小の入力float(0)を最小のunsigned charにマップし、範囲の最大のfloat(1.0f)を最大のunsignedバイト(255)にマップするマッピングが必要です。

4

2 に答える 2

15

a * 256f256から255に減らすためのチェックはどうですか?だから次のようなもの:

return (unsigned char) (min(255, (int) (a * 256f)));

(プラットフォームに適した最小関数の場合-C関数を思い出せません。)

基本的に、範囲を256の等しい部分に分割する必要があります。これは、それが行うべきことです。1.0が256になり、切り捨てが必要な場合のエッジケースは、ドメインが両端で包括的であるためです。

于 2009-03-01T16:05:57.243 に答える
1

あなたが探しているのはこれだと思います:

unsigned char QuantizeFloat (float a)
{
  return (unsigned char) (a * 256.0f);
}

これにより、[0, 1] の均一な浮動小数点値が [0, 255] の均一なバイト値にマップされます。[i/256, (i+1)/256[ ((i+1)/256 を除く) のすべての値は、0..255 の i に対して、i にマップされます。望ましくないのは、1.0f が 256.0f にマップされ、0 にラップすることです。

于 2009-03-01T16:45:10.127 に答える