c와 d 사이를 이동하기 위해 a와 b 사이에 숫자를 선형으로 매핑하는 방법은 무엇입니까?
즉, 2에서 6 사이의 숫자가 10에서 20 사이의 숫자에 매핑되기를 원하지만 일반화 된 경우가 필요합니다.
내 뇌가 튀어 나와.
답변:
숫자 X가 A와 B 사이에 있고 Y가 C와 D 사이에 속하도록하려면 다음 선형 변환을 적용 할 수 있습니다.
Y = (X-A)/(B-A) * (D-C) + C
그것은 당신이 원하는 것을 줄 것입니다. 비록 당신이 반대 방향으로 간격을 매핑 할 수 있기 때문에 당신의 질문은 약간 모호합니다. 0으로 나누는 것에주의하면 괜찮을 것입니다.
Y=f(X)=m*X+b
여기서 m과 b는 필요한 끝점에서 X와 Y의 값을 대체 한 다음 두 가지 제약 방정식에서 동시에 결정되었습니다. C=m*A+b
그리고D=m*B+b
X=A+(A-B)*t
이 접근 방식과 Peter의 접근 방식이 동등 함을 증명하기 위해 사용해야 했습니다. t는 기본적으로 X에서의 무차 원화 (이다 t=(X-A)/(A-B)
)
두 범위의 크기 사이의 비율을 구하기 위해 나눈 다음 초기 범위의 시작 값을 빼고 비율을 곱한 다음 두 번째 범위의 시작 값을 더합니다. 다시 말해,
R = (20 - 10) / (6 - 2)
y = (x - 2) * R + 10
이렇게하면 두 번째 범위의 첫 번째 범위에있는 숫자가 균등하게 분산됩니다.
이 기능은 java.lang.Math
광범위하게 필요한 기능이고 다른 언어로도 사용할 수 있기 때문에 클래스 에이 기능이 있으면 좋을 것 입니다. 다음은 간단한 구현입니다.
final static double EPSILON = 1e-12;
public static double map(double valueCoord1,
double startCoord1, double endCoord1,
double startCoord2, double endCoord2) {
if (Math.abs(endCoord1 - startCoord1) < EPSILON) {
throw new ArithmeticException("/ 0");
}
double offset = startCoord2;
double ratio = (endCoord2 - startCoord2) / (endCoord1 - startCoord1);
return ratio * (valueCoord1 - startCoord1) + offset;
}
이 코드를 미래에 대한 참조로 여기에 넣고 누군가에게 도움이 될 수 있습니다.
int srcMin = 2, srcMax = 6;
int tgtMin = 10, tgtMax = 20;
int nb = srcMax - srcMin;
int range = tgtMax - tgtMin;
float rate = (float) range / (float) nb;
println(srcMin + " > " + tgtMin);
float stepF = tgtMin;
for (int i = 1; i < nb; i++)
{
stepF += rate;
println((srcMin + i) + " > " + (int) (stepF + 0.5) + " (" + stepF + ")");
}
println(srcMax + " > " + tgtMax);
물론 0으로 나누는 검사를 사용합니다.
범위가 [a에서 b]이고 [c에서 d]로 매핑하려는 경우 여기에서 x는 매핑하려는 값입니다.이 공식을 사용합니다 (선형 매핑).
double R = (d-c)/(b-a)
double y = c+(x*R)+R
return(y)
https://rosettacode.org/wiki/Map_range
[a1, a2] => [b1, b2]
if s in range of [a1, a2]
then t which will be in range of [b1, b2]
t= b1 + ((s- a1) * (b2-b1))/ (a2-a1)