¿Cómo convertir un número de un conjunto min \ max a otro conjunto min \ max? [cerrado]

19

Estoy haciendo generación de terreno y tengo una biblioteca perlin que me da números aleatorios entre -1 y +1. Quiero convertir esto a la escala de 0-255. ¿Cuál es la forma apropiada de hacer esto?

Thraka
fuente

Respuestas:

23

La fórmula base es:

Result := ((Input - InputLow) / (InputHigh - InputLow))
          * (OutputHigh - OutputLow) + OutputLow;

Tu caso:

Resultado: = (( Entrada - -1 ) / ( 1 - -1 ) * ( 255 - 0 ) + 0 ;

Desde aquí puede optimizar la conversión si sus coeficientes son estáticos, pero el compilador probablemente también lo haga por sí mismo.

Resultado: = (( Entrada - -1 ) / 2 ) * 255 + 0 ;

Resultado: = Entrada * 127.5 + 127.5 ;

Kromster dice que apoya a Mónica
fuente
2
Esta respuesta tenía más sentido para mi cerebro programador. :) Un "gracias" a todos los demás por sus excelentes respuestas.
Thraka
10

El rango -1a 1es un rango total de 2. Por lo tanto, debe escalarlo adecuadamente para llegar 255. Algo como esto:

(randomPerlin + 1.0) * 127.5

Entonces agregas primero 1, para llegar a 0..2multiplicar luego 127.5para obtener un rango de0..255

bummzack
fuente
3

A través del poder de escala y sesgo.

De su valor, reste el valor mínimo de su rango. Eso le dará un valor en el rango [0..2].

Divida eso por el ancho del rango de origen, dándole un valor en el rango [0..1].

Multiplique eso por el ancho del rango objetivo, dándole un valor en el rango [0..255].

Agregue la base del rango objetivo para obtener un valor en el rango objetivo, que para este caso es el mismo que el paso anterior.

En resumen:

            (v - (-1.0)) 
v' = 0 + ---------------- * (255 - 0)
          (1.0 - (-1.0))
Lars Viklund
fuente
3
oldRange = oldMax - oldMin
newRange = newMax - newMin

newValue = ((oldValue - oldMin) * newRange / oldRange) + newMin

Espero que esto ayude.

functionoid
fuente
2

Traduzca el rango de entrada para que obtengamos el mínimo a cero agregando 1 (el valor negativo de la entrada mínima) -1 .. 1 -> 0 .. 2

Como el rango de salida comienza con cero, no haga nada por eso.

Escale el nuevo rango de entrada para que se ajuste al rango de salida, esto es fácil ya que ahora ambos comienzan en cero: multiplique el valor por 255/2 0..2 * 2/255 -> 0..255

¡Hecho!

Ejemplo:

0.5 irá: (0.5 + 1) * 127.5 = 191.25 -0.5 irá: (-0.5 + 1) * 127.5 = 63.75

Valmond
fuente
2

Digamos que xes entrada original y ysalida esperada. Tenemos al menos dos puntos (x, y) (-1, 0) (1, 255)

Como queremos hacer una interpolación lineal , podemos ver la ecuación de la forma y = m*x + c

Con los dos puntos anteriores, podemos resolver my una c vez hecho esto, obtienes la ecuación de transformación.

Tenga en cuenta que este método también funciona para otros tipos de ecuaciones. Por ejemplo, si desea una interpolación exponencial o cuadrática.

Ankush
fuente
En nuestro campo, el sentido común de la interpolación lineal tiende a ser que se mezcla de forma lineal entre dos cantidades con un factor de mezcla de esta manera: v = (1-a)*x + (a)*y. No veo cómo esta respuesta tiene mucha relevancia para la pregunta formulada, ya que todo lo que quiere es un mapeo de rango.
Lars Viklund
La cosa es que dos puntos en un plano definen de forma única una línea. Podemos tratar el mapeo de rango como una línea recta. y sabemos dos puntos en esa línea. resolverlo dará una ecuación lineal. puede ser interpolación lineal no es la palabra correcta aquí, pero quería decir un conjunto de puntos internos entre esos dos puntos en esta línea.
Ankush