将任意长度转换为介于-1.0和1.0之间的值?

时间:2010-06-18 03:23:27

标签: math range

如何将长度转换为-1.0到1.0范围内的值?

示例:我的舞台长度为440px并接受鼠标事件。我想点击舞台中间,而不是X = 220的输出,我希望它是X = 0。同样,我希望真正的X = 0成为X = -1.0,真正的X = 440成为X = 1.0

我无法访问舞台,因此我无法简单地对其进行居中注册,这将使此过程变得更加容易。此外,我无法动态更改舞台的实际大小,因此我正在寻找一个公式,将鼠标的舞台的实际X坐标平移到-1到1的范围内。

7 个答案:

答案 0 :(得分:11)

-1 + (2/440)*x

其中x是距离

因此,要概括它,如果最小标准化值为a且最大标准化值为b(在您的示例a = -1.0, b = 1.0中,最大可能值为k (在您的示例中为k = 440):

a + x*(b-a)/k

其中x>= 0<= k

答案 1 :(得分:4)

这基本上是两个步骤:

  1. 将范围居中于0,例如400到800之间的范围,因此它从-200到200.通过减去范围的最小值和最大值的中心(平均值)来实现此目的
  2. 除以极值范围的绝对值,从-n to n范围转换为-1 to 1范围。在-200到200的例子中,你除以200

答案 2 :(得分:3)

不回答你的问题,但是对于未来的google寻找连续monotone函数,将所有实数映射到(-1,1),任何sigmoid curve都可以,例如{{ 3}}或atan

f(x) = atan(x) / (pi/2)  
f(x) = 2/(1+e-x) - 1

(image alt text)

答案 3 :(得分:1)

(x - 220)/ 220 = new X

这就是你要找的东西吗?

答案 4 :(得分:1)

您需要移动原点并规范范围。所以表达式变为

(XCoordinate - 220) / 220.0

答案 5 :(得分:1)

您有一个时间间隔[a,b],您希望将其映射到新的时间间隔[c,d],并将原始坐标中的值x映射到{ {1}}在新坐标中。然后:

y

对于y = c + (x-a)*(c-d)/(b-a) [a,b] = [0,440]的示例,使用[c,d] = [-1,1]

x=220

等等。

顺便说一句,即使y = -1 + (220-0)*(1 - -1)/(440-0) = 0 超出x,这仍然有效。因此,只要您知道两个系统中的任何两个值,就可以在任一方向上转换任何值。

答案 6 :(得分:1)

处理任意阶段宽度(不知道你是否有线程要考虑,这可能需要互斥体或类似的,具体取决于你的语言?)

stageWidth = GetStageWidth(); // which may return 440 in your case
clickedX = MouseInput(); // should be 0 to 440
x = -1.0 + 2.0 * (clickedX / stageWidth); // scale to -1.0 to +1.0

您可能还想将x限制在[-1,1]范围内?

if ( x < -1 ) x = -1.0;
if ( x >  1 ) x =  1.0;

或提供某种反馈/警告/错误,如果它超出界限(仅当真的很重要并且只是将其剪切到范围[-1,1]不够好)