Mar*_*zzo 11 javascript math performance normalization
我正在尝试创建一个函数,它接受一个数字并将其从最小和最大边界之间的0 - 1标准化.例如:
如果我想将值10标准化为5到15之间,我称之为:
val = 10; normalize(val, 5, 15); 返回0.5
将值0标准化为-10到5之间
val = 0; normalize(val, -10, 5); 返回0.666
这是我提出的功能:
function normalize(val, min, max){
// Shift to positive to avoid issues when crossing the 0 line
if(min < 0){
max += 0 - min;
val += 0 - min;
min = 0;
}
// Shift values from 0 - max
val = val - min;
max = max - min;
return Math.max(0, Math.min(1, val / max));
}
Run Code Online (Sandbox Code Playgroud)
我的问题是:这是规范化一维值的最有效方法吗?我将以每帧60fps的速度调用此函数几千次,因此我希望尽可能优化它以减少计算负担.我已经找到了归一化公式,但我找到的只是二维或三维解.
小智 35
为什么不呢:
__CODE__
Nin*_*olz 10
使用Nathan Bertons对一些具有相同值min和max值的预配置函数的答案,您可以使用它.
function normalize(min, max) {
var delta = max - min;
return function (val) {
return (val - min) / delta;
};
}
console.log([5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15].map(normalize(5, 15)));Run Code Online (Sandbox Code Playgroud)
当我想用已知的最小值、最大值对两个范围之间的值进行归一化时,我更喜欢使用这个公式。您可以添加检查以约束输入,但如果将超出范围的值作为输入,这将正确计算与新范围的差异。
/**
* Normalizes a value from one range (current) to another (new).
*
* @param { Number } val //the current value (part of the current range).
* @param { Number } minVal //the min value of the current value range.
* @param { Number } maxVal //the max value of the current value range.
* @param { Number } newMin //the min value of the new value range.
* @param { Number } newMax //the max value of the new value range.
*
* @returns { Number } the normalized value.
*/
const normalizeBetweenTwoRanges = (val, minVal, maxVal, newMin, newMax) => {
return newMin + (val - minVal) * (newMax - newMin) / (maxVal - minVal);
};
const e = document.getElementById('result');
e.innerHTML = normalizeBetweenTwoRanges(10, 5, 15, 0, 1);Run Code Online (Sandbox Code Playgroud)
<span id="result"></span>Run Code Online (Sandbox Code Playgroud)
小智 5
Using Nathan Bertons's answer, you must validate if max-min is equal to zero, otherwise the return will be NaN:
function (val, max, min) {
if(max - min === 0) return 1; // or 0, it's up to you
return (val - min) / (max - min);
}
Run Code Online (Sandbox Code Playgroud)
and you can use a generalization to restrict the range of values in the dataset between any arbitrary points a and b using:
function (val, max, min) {
if(max - min === 0) return a; // or b, it's up to you
return a + (((val - min) * (b-a)) / (max - min));
}
Run Code Online (Sandbox Code Playgroud)