Я посмотрел источники libnoise и нашел функцию ValuNoise3D:
double noise::ValueNoise3D (int x, int y, int z, int seed)
{
return 1.0 - ((double)IntValueNoise3D (x, y, z, seed) / 1073741824.0);
}
int noise::IntValueNoise3D (int x, int y, int z, int seed)
{
// All constants are primes and must remain prime in order for this noise
// function to work correctly.
int n = (
X_NOISE_GEN * x
+ Y_NOISE_GEN * y
+ Z_NOISE_GEN * z
+ SEED_NOISE_GEN * seed)
& 0x7fffffff;
n = (n >> 13) ^ n;
return (n * (n * n * 60493 + 19990303) + 1376312589) & 0x7fffffff;
}
Но когда я смотрю на это, это волшебство для меня. Как это на самом деле работает? Я имею в виду, почему парень, который написал это, взял эти простые числа вместо других? Почему такие уравнения? Как он решил использовать эти уравнения вместо других? Просто … как это понять?
веб-сайт libnoise имеет хорошее объяснение математики, стоящей за этой шумовой функцией. В частности, что касается простых чисел:
Эти большие целые числа являются простыми числами. Эти целые числа могут быть изменены, пока они остаются простыми; не простые числа могут вводить различимые шаблоны в вывод.
noise::IntValueNoise3D
фактически работает в два этапа: первый шаг преобразует координаты (x, y, z) в одно целое число, а второй шаг помещает это целое число через целочисленную шумовую функцию, чтобы получить значение шума примерно между -1073741824 и 1073741824. noise::ValueNoise3D
просто преобразует это целое число в значение с плавающей точкой между -1 и 1.
Почему noise::IntValueNoise3D
выполняет все эти запутанные операции, в основном сводится к тому, что эта конкретная последовательность операций приводит к хорошему, шумному результату без видимого четкого шаблона. Это не единственная последовательность операций, которую можно было использовать; все, что дает достаточно шумный результат, сработало бы.
Есть искусство случайности. Есть много вещей, которые делают псевдослучайное число «хорошо выглядеть». Для многих трехмерных функций самое главное, чтобы они выглядели хорошо, — это правильно выглядящее распределение частот. Все, что обеспечивает хорошее распределение частоты по модулю 2 ^ 32, даст очень хорошо выглядящие числа. Умножение на большое простое число дает хорошие распределения частот, потому что они не имеют общих коэффициентов с 2 ^ 32.