1. 矩形平铺假设的根本性几何缺陷
在墨卡托等二维平面地图投影中,地球被展开为一个平面矩形,纬度范围为-90°到+90°,经度范围为-180°到+180°。
许多初级编程教程建议使用如下简单的平面随机公式:
// ❌ Naive algorithm (Suffers from polar bias bug) const latitude = (Math.random() * 180) - 90; const longitude = (Math.random() * 360) - 180;
虽然这行代码能输出有效数字,但它错误地将所有纬度带视为拥有相同的物理表面积。在真实的3D球体上,纬度圈的实际周长是纬度余弦值的函数:
在赤道(0°)处,周长约为40,075公里;而在北纬80°(格陵兰岛附近),周长缩减至仅6,950公里。平面算法在北极附近的点密度是赤道的5.7倍!
2. Marsaglia球面等面积正弦变换算法
为了在球体表面生成完全均匀分布的点,概率密度必须与微分表面积元素严格成正比:
由于微分面积与d(sin θ)成正比,我们只需在区间[-1, 1]内均匀抽取sin(θ):
// ✅ Correct Archimedes-Lambert-Marsaglia equal-area algorithm:
function getRandomSpherePoint() {
const u = Math.random(); // Uniform in [0, 1)
const v = Math.random(); // Uniform in [0, 1)
// Invert the cumulative distribution function:
const sinLat = 2 * u - 1; // Uniform in [-1, 1]
const latRad = Math.asin(sinLat); // In radians
const lat = latRad * (180 / Math.PI); // In degrees [-90, +90]
const lng = -180 + v * 360; // In degrees [-180, +180]
return { lat, lng };
}这个优雅的数学变换从根本上保证了地球上的每一平方公里都具有完全均等的入选概率。
3. 陆地排除采样与PRNG确定性复现
地球表面约71%为水域。当用户选择“仅限陆地”模式时,算法采用高效的排除采样法:
- 生成一个等面积球面坐标点。
- 利用各大洲边界多边形与自然陆地矢量数据进行高速点面拓扑相交测试。
- 若点落入海洋,则自动丢弃并重新抽取,上限为250次。
为了满足科研与复现需求,我们结合了53位cyrb53字符串哈希与32位mulberry32伪随机数生成器,确保相同种子100%输出相同结果。