尝试将.dem文件转换为.grid文件时,DLL加载DLL失败错误

时间:2018-02-18 16:52:11

标签: python dll load gdal

我一直试图找到一种免费且简单的方法将.dem文件转换为.grid文件,而且我一直在努力获取一个在线的python程序。我一直在收到一个我不理解的错误,在网上查询已经告诉我人们之前已经犯过这个错误,但不一定是在我发现它的情况下,所以他们的解决方案涉及安装不同于我需要的模块。

这是我的python安装:

Python 3.4.0 (v3.4.0:04f714765c13) [MSC v.1600 64 bit (AMD64)] on win32

以下是我安装所需模块的方法,名为osgeo。我按照上面的python安装步骤进行了操作,确保我使用了正确的版本: Instructions I used 按照这些说明允许我通过osgeo不存在的错误,所以至少我在这方面取得了一些进展。

以下是我一直试图运行的代码:

import sys
import os
import osgeo.gdal as gd
from gdalconst import GA_ReadOnly, GDT_Byte, GDT_UInt16, GDT_Int16, \
     GDT_UInt32, GDT_Int32, GDT_Float32, GDT_Float64
import struct

# GDAL data types to packt data_types
gd_type = {GDT_Byte:    "b",
           GDT_UInt16:  "H",
           GDT_Int16:   "h",
           GDT_UInt32:  "I",
           GDT_Int32:   "i",
           GDT_Float32: "f",
           GDT_Float64: "d"}
# establish input file
ifilename = r"C:\Users\Nick\Desktop\sample.dem"
# generate output file name 
ofilename = os.path.splitext(ifilename)[0] + ".grid"
# use gdal to read DEM file
idataset = gd.Open(ifilename, GA_ReadOnly)
if idataset is None:
    print("Cannot read input file {}".format(ifilename));
    sys.exit(2)
# get size of dem
cols = idataset.RasterXSize
rows = idataset.RasterYSize
# get and calculate coordinate limits
tr = idataset.GetGeoTransform()
xul = tr[0]
yul = tr[3]
xlr = xul + (cols - 1) * tr[1] 
ylr = yul + (rows - 1) * tr[5]
# write data to binary output
of = open(ofilename, "wb")
of.write(struct.pack("2i", cols, rows))
of.write(struct.pack("4f", xul, ylr, xlr, yul))
band = idataset.GetRasterBand(1)
d = band.ReadRaster(0, 0, cols, rows, cols, rows, band.DataType)
data = struct.unpack(gd_type[band.DataType] * (rows * cols), d)
of.write(struct.pack("f" * (cols * rows), *data))
of.close()

这是我的错误消息:

Traceback (most recent call last):
  File "C:/Users/Nick/Desktop/demtogrid.py", line 3, in <module>
    import osgeo.gdal as gd
  File "C:\Python34\lib\site-packages\osgeo\__init__.py", line 21, in <module>
    _gdal = swig_import_helper()
  File "C:\Python34\lib\site-packages\osgeo\__init__.py", line 17, in swig_import_helper
    _mod = imp.load_module('_gdal', fp, pathname, description)
  File "C:\Python34\lib\imp.py", line 243, in load_module
    return load_dynamic(name, filename, file)
ImportError: DLL load failed: The specified module could not be found.

我还尝试了来自this forum的其他代码,例如名为 siki 的用户代码,但我的所有尝试都以与所示相同的错误结束了在上面的例子中。

感谢任何帮助过的人。同样,它不是一个为我做转换的python脚本,我只需要一个免费的方法将.dem转换为.grid,而像ArcGIS这样的典型程序不是免费的。

1 个答案:

答案 0 :(得分:1)

您没有将%PATH% env var设置为右侧。我设法重现了这个问题,并修复了它。我采取的一些步骤与常规步骤不同,原因我稍后会解释:

  • 我的机器上安装了~10个 Python (一些安装,一些由我构建 - 使用不同的编译器;大多数是 x64 ,有些是 VEnv ed,但这不应该有任何区别), Python3.4 x64 (使用编译器 v1.600 - VStudio 10.0构建) )就是其中之一
  • 将代码保存在我的计算机上( code.py )。运行它,(显然)失败了:

    (py34x64_test) E:\Work\Dev\StackOverflow\q048854161>"e:\Work\Dev\VEnvs\py34x64_test\Scripts\python.exe" code.py
    Traceback (most recent call last):
      File "code.py", line 3, in <module>
        import osgeo.gdal as gd
    ImportError: No module named 'osgeo'
    
  • 下载:

    1. [GISInternals]: release-1600-x64-gdal-2-2-3-mapserver-7-0-7.zip - 单个.zip包中的编译二进制文件
    2. [GISInternals]: GDAL-2.2.3.win-amd64-py3.4.msi - GDAL python绑定的安装程序(需要安装GDAL内核)
  • 解压缩(在当前目录中):
    • #1。在名为 gdal 的目录中 - 只需将其解压缩
    • 在名为 gdal_py 的目录中
    • #2。 - 运行msiexec /a GDAL-2.2.3.win-amd64-py3.4.msi TARGETDIR="E:\Work\Dev\StackOverflow\q048854161\gdal_py"msiexec&#39; s {strong>管理员安装,如[SU]: How do I extract files from an MSI package?所示,查看[MSDN]: Command-Line Options了解详情
      • 由于正常安装会将相关文件放在 Python 安装目录中,因此它也会模仿它们,因此相关文件实际安装在&#34; gdal_py \ Lib \ site-packages中&#34;为了简单起见,我将它们移动了2个文件夹(直接在 gdal_py 目录中)
    • 我这样做了,因为我不想用 pkg 污染我的 OS ,我可能只会使用一次,所以我希望这两个只与这个问题有关。当然,这是一个额外的麻烦(只是开玩笑:)),这不会发生在常规安装过程中
  • gdal_py 添加到%PYTHONPATH%(不需要定期安装#2。,因为文件已经在 Python 的模块搜索路径 - 检查我之前必须做的移动操作,然后再次运行它,产生了:

    (py34x64_test) E:\Work\Dev\StackOverflow\q048854161>set PYTHONPATH=%PYTHONPATH%;gdal_py
    
    (py34x64_test) E:\Work\Dev\StackOverflow\q048854161>"e:\Work\Dev\VEnvs\py34x64_test\Scripts\python.exe" code.py
    Traceback (most recent call last):
      File "code.py", line 3, in <module>
        import osgeo.gdal as gd
      File "E:\Work\Dev\StackOverflow\q048854161\gdal_py\osgeo\__init__.py", line 21, in <module>
        _gdal = swig_import_helper()
      File "E:\Work\Dev\StackOverflow\q048854161\gdal_py\osgeo\__init__.py", line 17, in swig_import_helper
        _mod = imp.load_module('_gdal', fp, pathname, description)
      File "e:\Work\Dev\VEnvs\py34x64_test\lib\imp.py", line 243, in load_module
        return load_dynamic(name, filename, file)
    ImportError: DLL load failed: The specified module could not be found.
    
  • 这正是您的错误。因此,它尝试加载 _gdal.pyd 并失败,不是因为它无法找到它,而是因为(某些)其依赖项无法找到(此处,错误消息具有误导性) ,如果找不到模块,则错误将是:ImportError: No module named '_gdal')。
    下面是Dependency Walker中加载的 _gdal.pyd 的图片。请注意,常规#2。安装将其置于%PYTHON34X64_INSTALL_DIR%\ Lib \ site-packages \ osgeo 之下(这不是真正的环境变量,只是一个路径占位符):

    _gdal.pyd

  • 如图所示,它取决于 gdal202.dll 。因此,当导入 _gdal.pyd 时, OS 需要找到所有依赖项:请注意,这是递归(依赖项,依赖项& #39;依赖关系,等等)。这就是本教程中%PATH% env var设置的内容。对我来说,最简单的方法是添加 gdal202.dll dir(因为它是#1。的一部分,它将是 gdal \ bin )到%PATH%[MSDN]: Dynamic-Link Library Search Order):

    (py34x64_test) E:\Work\Dev\StackOverflow\q048854161>set PATH=%PATH%;gdal\bin
    
    (py34x64_test) E:\Work\Dev\StackOverflow\q048854161>"e:\Work\Dev\VEnvs\py34x64_test\Scripts\python.exe" code.py
    ERROR 4: C:\Users\Nick\Desktop\sample.dem: No such file or directory
    Cannot read input file C:\Users\Nick\Desktop\sample.dem
    
  • 有效!好吧,它没有用,因为你的脚本中还有其他东西我没有,但成功通过了这一步。现在,脚本中可能存在错误,这会阻止您实现目标,但这些错误与当前问题无关。