8bit値(0..255など)の値とユーザが取り扱いやすい0..1000(千分率, ‰)値でスケール(拡縮)する。低い演算コストで実施するため、除算(
x*1000/255
)の替わりに乗算とビットシフトによって近似計算します。
static inline uint8_t scale_1000_to_127u8(uint16_t x)
static inline uint16_t scale_127u8_to_1000(uint8_t x)
static inline uint8_t scale_1000_to_255u8(uint16_t x)
static inline uint16_t scale_255u8_to_1000(uint8_t x)
static inline uint8_t scale_1000_to_256u8(uint16_t x)
static inline uint16_t scale_256u16_to_1000(uint16_t x)
scale_1000_to_127u8()
0..1000 を 0..127 にスケールします。(16646*x+65000)>>17
を用いて近似計算します。
scale_127u8_to_1000()
0..127 を 0..1000 にスケールします。(2064000UL*x+131072)>>18
を用いて近似計算します。
scale_1000_to_255u8()
0..1000 を 0..255 にスケールします。(33423*x+65000)>>17
を用いて近似計算します。
scale_255u8_to_1000()
0..255 を 0..1000 にスケールします。(1028000UL*uint32_t(x)+131072)>>18
を用いて近似計算します。
scale_1000_to_256u8()
0..1000 を 0..256 にスケールします。(33554*x+66000) >> 17
を用いて近似計算します。
注: x=999,1000は計算値が256になりますがuint8_t
の範囲として255を返します。
scale_256u16_to_1000()
0..256 を 0..1000 にスケールします。(1028000UL*uint32_t(x)+131072)>>18
を用いて近似計算します。
背景
ハードウェアに設定すべき値は0..255といった2進数が前提になることが多く、ユーザアプリケーションで取り扱う数は0..1000といった10進数基準のほうが扱いやすい。これらのスケール変換に除算を行わない式を定義した。