首页 > 解决方案 > 有没有办法改变 topojson 文件中的投影?

问题描述

我正在尝试创建一个使用 geoAlbersUsa 投影的 topojson 文件,该文件源自美国人口普查局的 ZCTA(本质上是邮政编码)shapefile。我能够使用指定的地图成功通过优秀的ht​​tps://medium.com/@mbostock/command-line-cartography-part-1-897aa8f8ca2c中的示例,现在我正在尝试获得相同的结果使用邮政编码级别的 shapefile。

由于文件的大小和文件中字符串的长度,我不断遇到各种问题。虽然我已经能够创建一个 geojson 文件和一个 topojson 文件,但我无法给它我想要的 geoAlbersUsa 投影。我希望找到一些东西来将当前的 topojson 文件转换为带有 geoAlbersUsa 投影的 topojson 文件,但我找不到任何方法。

我知道这可以在浏览器中以编程方式完成,但我所阅读的所有内容都表明,如果尽可能多地首先在文件本身中完成,性能将会显着提高。

尝试 1:我能够使用 shp2json(如 Mike Bostock 的示例)成功地将 ZCTA 级 shapefile 转换为 geojson 文件,但是当我尝试运行 geoproject(来自 d3-geo-projection)时,我收到与字符串长度过长有关的错误. 在节点(使用 npm)中,我安装了 d3-geo-projection(npm install -g d3-geo-projection)然后运行以下命令:

地质工程“d3.geoAlbersUsa()”< us_zips.geojson > us_zips_albersUsa.json

我收到错误消息,指出“错误:无法创建长度超过 0x3fffffe7 个字符的字符串”

尝试2:我使用ogr2​​ogr(https://gdal.org/programs/ogr2ogr.html)创建geojson文件(而不是shp2json),然后尝试运行与上面相同的geoproject代码并得到相同的错误。

尝试 3:我使用 ogr2ogr 创建 geojson 序列文件(而不是 geojson 文件),然后运行 ​​geo2topo 从 geojsons 文件创建 topojson 文件。虽然这成功创建了 topojson 文件,但它仍然没有在生成的 topojson 文件中包含 geoAlbersUsa 投影。

我从 ogr2ogr 的相当迟钝的文档中得到,可以使用 -a_srs 指定输出投影,但我一生都无法弄清楚如何指定可以让我得到 geoAlbersUsa 投影的东西。我找到了这个参考https://spatialreference.org/ref/sr-org/44/但我认为这会让我得到阿尔伯斯,它可能会切断阿拉斯加和夏威夷,这不是我想要的。

这里有什么建议吗?我希望我能找到一种方法来更改 topojson 文件本身中的投影,因为这样可以避免每当我尝试在节点中执行任何需要使用 geojson 文件的操作时遇到的过长字符串问题. 似乎这可能是可以在早期版本的 topojson 中完成的事情(请参阅投影 topojson 的方法?),但我现在看不到任何方法。

标签: topojsonmap-projectionsogr2ogr

解决方案


不完全是答案,但不仅仅是评论..

所以,我在谷歌上搜索了“ 0x3fffffe7 ”,并在一个随机的 Github/NodeJS 项目上找到了这个评论,根据阅读它,我的直觉是节点的东西,和/或你正在使用的 D3 东西正在减少你的整个 ZCTA级 shapefile 到 ....存储在内存中的单个字符串!这对于具有如此精细细节的大陆比例地图来说并不好。

此外,留下该评论的人建议,在这种情况下,OP 需要一种不同的方法来将他们的数据集介绍给客户。(我想是浏览器?)在您的情况下,如果您将每个州的 zip 集合查询到单个 shapefile 中(ogr2ogr 可以使用OGR-SQL执行此操作),它可能会起作用,这将为您提供 5 个不同的 shapefile。然后对于其中的每一个,通过您的转换运行它们以获取 json/geoalbers。要测试这个概念,请尝试只导出一个状态,看看其他一切是否按预期工作。

话虽这么说,我担心你对这个项目的方法有一个不可行的 UI/架构期望:我只是不认为你可以把那么多地理数据放在浏览器 DIV 中!DIV 有多大,我希望全屏?!?

我的建议是想出一种不同的方式来呈现数据。例如,插入 DIV 以“选择您的状态”,然后单击状态将主 DIV 缩放到该状态的更大视图,同时使用您使用准备的 50 个文件下拉和排序该状态的特定 ZCTA 级别数据我上面提到的策略。那有意义吗?

这是一个快速示例,说明我希望您如何将 OGR_SQL 应用于您的场景,适应:

ogr2ogr idaho_zcta.shp USA_zcta.shp -sql "SELECT * FROM USA_zcta WHERE STATE_NAME = 'ID'"

参数如下:

  • idaho_zcta.shp < 这是你的新文件
  • USA_zcta.shp < 这是你的源 shapefile
  • -sql < 这表示 OGR_SQL 查询表达式

至于查询本身,有几个提示。首先,将整个查询字符串用双引号括起来。如果发生奇怪的事情,请尝试在查询的开头和结尾添加前导和尾随空格,例如..

" SELECT ... 'ID' "

我知道这很奇怪,但我曾经遇到过这种情况,它只能这样工作。

其次,相对于查询,表名与shapefile名称相同,只是没有“.shp”文件扩展名。我不记得 shapefile 名称和查询字符串的表名之间是否区分大小写。如果遇到问题,请给出 shapefile 和所有小写名称并在 SQL 中也使用小写。

至于你的投影转换——你自己在那里。geoAlbersUSA看起来不是行业标准(即 EPSG 编码),并且是特定于 D3 的,专门用于浏览器所以 ogr2ogr 不会处理它。但我同意提前转换数据的策略。希望您已经研究过的转换管道能够工作,如果您只有更小的(即州级)数据集要通过它。

祝你好运。


推荐阅读