Edited at

地域メッシュの計算にはミリ秒を使うべき

More than 1 year has passed since last update.


地域メッシュの仕様と抽象化

地域メッシュは1次メッシュ「緯度差は40分、経度差は1度」を分割したものです。

└─第1次 (約80km)

└─第2次(縦横8分割 約10km)
├─第3次(基準) (縦横10分割 約1km)
│ ├─10分の1 (縦横10分割 約100m)
│ ├─20分の1 (縦横20分割 約50m)
│ └─2分の1 (縦横2分割 約500m)
│ └─4分の1 (縦横2分割 約250m)
│ └─8分の1 (縦横2分割 約125m)
├─5倍 (縦横2分割 約5km)
└─2倍 (縦横5分割 約2km)

上の親子関係通り、緯度差/経度差を分割していけば起点と辺長が求まるので面を作成することが可能です。


緯度差 = 40/60

経度差 = 1

のみあればメッシュコード起点から分割していくだけで面を貼れます。


小数点誤差の積み重ねとミリ秒単位での計算

緯度差は40分の時点でわかる話ですがこれを積み重ねるとずれます。

var xdiff = 1;

var ydiff = 40/60;

var xorg = 134;
var yorg = 34;

var neX = xorg + xdiff * 2 * 8;
var neY = yorg + ydiff * 2 * 8;

console.log(neX);//135
console.log(neY);//34.666666666666664

10進緯度経度

var xdiff = 1;

var ydiff = 40/60;

var xorg = 135;
var yorg = 34.666666666666664;

var neX = xorg + xdiff * 2 * 8;
var neY = yorg + ydiff * 2 * 8;

console.log(neX);//136
console.log(neY);//35.33333333333333

//ミリ秒単位
console.log(neX *3600000); //489600000
console.log(neY *3600000); //127199999.99999999

ミリ秒

var xdiff = 3600000 / 8 / 2;

var ydiff = 2400000 / 8 / 2;

var xorg = 486000000;
var yorg = 124800000;

var neX = xorg + (xdiff * 2 * 8);
var neY = yorg + (ydiff * 2 * 8);

console.log(neX);//489600000
console.log(neY);//127200000

console.log(neX / 3600000);//136
console.log(neY / 3600000);//35.333333333333336

緯度経度に直す時点まではなるべくミリ秒単位で計算すべきでしたと言う話。。

地域メッシュをブラウザ上で作成するライブラリを作成した話

ミリ秒 修正前後をMapshaperで確認すると1次メッシュ単位で緯度方向の面が重なってしまっている様子。( 左下隅からの積み重ねなので )

Typescriptで作成していた為、型の変数変更→依存部分修正と割と楽に修正できましたとさ。

修正前

lineIntersections.jpg

修正後

noerror.jpg