Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/125.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 整数值的缩放(从浮点)_C++_Floating Point_Int_Scale_Midi - Fatal编程技术网

C++ 整数值的缩放(从浮点)

C++ 整数值的缩放(从浮点),c++,floating-point,int,scale,midi,C++,Floating Point,Int,Scale,Midi,我正在设计一个VST音频插件,它需要从传入信号中提取振幅数据,用于midi域中的速度设置 本质上,我将接收0-1(浮点)之间的值,并需要将它们转换为0-127 int 目前,该过程是将浮点值乘以100,得到+3个小数位的整数值,即103.4567685或005.67787282 从这里开始,我将使用floor()函数将浮点数四舍五入为整数 但是,这将给我留下0-100之间的值;但是,我需要将其缩放到0-127 任何关于如何实现这一点的建议都将不胜感激。我想我一定错过了什么。为什么不乘以127.0

我正在设计一个VST音频插件,它需要从传入信号中提取振幅数据,用于midi域中的速度设置

本质上,我将接收0-1(浮点)之间的值,并需要将它们转换为0-127 int

目前,该过程是将浮点值乘以100,得到+3个小数位的整数值,即103.4567685或005.67787282

从这里开始,我将使用floor()函数将浮点数四舍五入为整数

但是,这将给我留下0-100之间的值;但是,我需要将其缩放到0-127


任何关于如何实现这一点的建议都将不胜感激。

我想我一定错过了什么。为什么不乘以127.0而不是100?

在使用
floor()
之前,将结果值乘以1.27?

只需将值乘以127并将其转换为
int
<代码>[0,1]*127=>[0127]

范围转换并不是那么简单。在将整数范围[-n;n]缩放为浮点的情况下,使用简单乘法的简单方法会产生这样的效果,逆映射可能不会映射到原始值。假设在整数范围内有一组所有数字,在浮点范围内有一组大小相同的数字,则朴素映射不是双射的


关于这篇文章和示例代码,有一篇很好的文章,介绍了如何在

实现单调性和保序映射。如果您接受这里给出的一些建议并乘以127,您会发现127在输出中并没有很好地表示出来。也许这对你来说不会是个问题,但是有一个小小的改变会带来很大的不同

你可能认为四舍五入会有帮助,但事实并非如此。127处的值数量仍然只有其他值的一半,现在0处的值数量也将是平均值的一半

正确的公式是:

int amplitude = static_cast<int>(value * (128-epsilon)); // where epsilon is a very small floating point value
int振幅=静态_投射(值*(128 epsilon));//其中epsilon是一个非常小的浮点值

正确的方法是:

int amplitude = 128 * value ;
if (amplitude == 128) amplitude = 127 ;

在round()函数的帮助下,我使用这种有效的解决方法来覆盖所有的值

输出=圆形(ampiezza*127.5+127.5)

ampiezza是介于-1到+1之间的有符号浮点 输出为8位整数

输出范围从0到255,以127和128为中心


希望这能有所帮助。

哦,是的。我没想到。我觉得自己像个傻瓜,如果你不告诉可怜的OP如何获得ε,你就不能给出这样的建议!100对他来说似乎是可以接受的,所以127可能是/曾经是,但他可能没有想到或注意到这一点@TonyK,epsilon的精确值对于大多数实际应用来说并不十分重要。您可以使用
limits.h中的
FLT\u EPSILON
numeric\u limits::EPSILON()
中的
limits
,或仅使用任意小数值。我不会使用
numeric\u limits::epsilon()
,因为它只对1.0的值有效,对128.0来说太小了。你没有回答我的问题。(请参阅我的答案了解一些常识。)-1:这并不能正确映射所有值-请参阅例如TonyK的答案或Mark R的答案以了解更好的解决方案TonyK是正确的。原因是,64是MIDI的中心值,MIDI设备中的实现通常使用上述方法。