张春成

V2

2022/10/30阅读:17主题:默认主题

地铁密度对比

地铁密度对比

在某个神奇的国度,不是每个人都有把握方向盘的权力,因此,地铁就是出行的主力。

本文试图通过蜂窝状的风格进行计数,用来对各个地区的地铁方便程度进行量化。

本文代码可见我的前端笔记本

Subway stations in hex grids[1]


上海地铁

首先,经过分析来看,上海中心区的地铁看是去是最密集和方便的。它表现在几乎全部蜂窝风格内都有地铁覆盖,并且密度最大的地区甚至能够包含 5 条地铁线路。

Snipaste_2022-10-30_17-02-56.png
Snipaste_2022-10-30_17-02-56.png

北京地铁

在同样比例尺和蜂窝密度下,北京地铁的密度和方便程度就显得稍逊一筹。除了中央的紫禁城之外,城区仍然有大量的“空隙”无地铁可坐,另外,地铁站最密的地方也仅有 4 条线路可坐。

Snipaste_2022-10-30_17-03-16.png
Snipaste_2022-10-30_17-03-16.png

天津地铁

天津地铁,其实我也不知道它为什么会出现在这个地方。和上述两个城市相比,只能说有就不错了,要啥自行车。

Snipaste_2022-10-30_17-03-38.png
Snipaste_2022-10-30_17-03-38.png

Mapbox 相关

本文的代码是基于 Mapbox 的 GL JS 包构建的,它非常的好用

首先,它提供的 zoom 设置可以用于对视野大小进行规范比较,调整的大原则如下表。地铁密度统计都是在 zoom level = 10 的视野下绘制的,因此可以用来反应城市的“大路”体系。

At zoom level You can see
0 The Earth
3 A continent
4 Large islands
6 Large rivers
10 Large roads
15 Buildings

其次,它提供了足够丰富的 Layer 接口,这些蜂窝就是以 Layer 的形式绘制的。它与 GeoJson 格式联动,能够实现多种效果的渲染。尤其是这种渲染是动态的,用户可以通过绑定行为的方式进行动态重绘。

// Add handlers
{
  map.on("dragend", () => {
    console.log("dragend");
    reDraw();
  });

  map.on("zoomend", () => {
    console.log("zoomend");
    reDraw();
  });

  map.on("pitchend", () => {
    console.log("pitchend");
    reDraw();
  });
}

值得注意的是,这些重绘的方法不会相互覆盖,而是会形成一种类似操作栈的结构。这种行为在文档中并没有给出,因此有理由相信这是一个未定义的行为,也可能是一种 BUG。如果你的设计是依赖于它们相互覆盖的话,它会导致“应该被覆盖的函数”被反复执行,从而大大降低执行效率。

// It will trigger both fun1 and fun2 on draggend,
// and the fun2 will not override fun1 on draggend.
{
 map.on("dragend", () => {
     console.log("dragend");
     fun1();
   });
 
 map.on("dragend", () => {
     console.log("dragend");
     fun2();
   });
}

最后,last but not least,重绘方法 reDraw 内的函数是以“快照”的形式传入系统。也就是说,如果它动态引用一些参数,这些参数最好不要放在另外的函数堆栈里,而是要绑定在 map 上。如果放在另外的函数堆栈里,map 在 Runtime 时不会追踪这些值的更改,从而导致异常。

参考资料

[1]

Subway stations in hex grids: https://observablehq.com/@listenzcc/mapbox-with-hex-grids-version-3

分类:

后端

标签:

后端

作者介绍

张春成
V2