
本文共 4821 字,大约阅读时间需要 16 分钟。
GDAL介绍:
GDAL(Geospatial Data Abstraction Library)是一个开源栅格空间数据转换库。它利用抽象数据模型来表达所支持的各种文件格式。它还有一系列命令行工具来进行数据转换和处理。
GDAL使用C++开发,因此要在Java环境下使用GDAL库,要用JNI(Java跨平台调用的一种方式)的方法调用dll库。所以,我们可以下载GDAL的源码,依照官网教程,通过Visual Studio编译出可用dll。但是最简单的做法就是使用已经编译生成好的符合JNI标准的动态dll库和jar包了,推荐这个网址:,下载合适的文件。
例如我下载的是release-1800-x64-gdal-2-2-3-mapserver-7-0-7,里面包含了编译好的GDAL以及jar包。
下面以Eclipse的配置为例,示范如何在Java环境中调用GDAL库(此时假设所有GDAL的dll都已经编译好,或是从上面写的网址下载下来了):
1.将下载下来的压缩包解压至合适位置,内容列表如下:
2. 打开Eclipse,新建一个普通的java工程。
3.将下载下来的压缩包bin/gdal/java目录下的gdal.jar、gdalconstjni.dll、gdaljni.dll、ogrjni.dll、osrjni.dll文件拷贝到刚才新建的java工程目录下,如下图,和src目录同级。
4.右键gdal.jar,在弹出的菜单中选择Build Path -> Add to Build Path,将gdal.jar引入到工程环境中
这时候写代码,Eclipse编译不会有错误,但是运行程序时会报错,于是还要进行下一步:
5.将下载下来的压缩包bin目录下的所有dll文件(这些文件是GDAL相关的dll文件,是GDAL_Java的dll需要调用的)拷贝至正确的位置,有很多地方可选:
1)java工程目录下(我用的是这种方法,让dll文件跟着项目一块)。
2){JAVA_HOME}jre/bin,也可以采用这种做法,将这些dll拷贝至jdk安装目录下的jre下的bin目录下。
3)网上有人说拷贝至{windir}system32目录下,此方法没有检验过
6. 新建一个HelloGDAL类来执行转换,代码如下:
package com.ysq.gdal;import org.gdal.gdal.Band;import org.gdal.gdal.Dataset;import org.gdal.gdal.Driver;import org.gdal.gdal.gdal;import org.gdal.gdalconst.gdalconstConstants;import org.gdal.ogr.DataSource;//import org.gdal.ogr.Driver;import org.gdal.ogr.ogr;public class HelloGDAL { public static void main(String[] args) { //此处换成自己文件的位置的路径 //readGDAL("E:\\xxxxxxx.tif"); getElevationFromTif("E:\\xxxxxxx.tif"); } /** * 读取tif文件的相关信息 * @param fileName */ public static void readGDAL(String fileName) { gdal.AllRegister(); //读取影像数据 Dataset dataset = gdal.Open(fileName,gdalconstConstants.GA_ReadOnly); if(dataset == null){ System.err.println("GDALOpen failed - "+gdal.GetLastErrorNo()); System.err.println(gdal.GetLastErrorMsg()); System.exit(1); } Driver driver = dataset.GetDriver(); System.out.println("Driver:"+driver.getShortName()+"/"+driver.getLongName()); //读取影像信息 int xSize = dataset.getRasterXSize(); int ySize = dataset.getRasterYSize(); int bandCount = dataset.GetRasterCount(); System.out.println("size is "+xSize+","+ySize+",光带数:"+bandCount); Band band = dataset.GetRasterBand(1); int type = band.GetRasterDataType(); //type为1,代表的是Eight bit unsigned integer System.out.println(type); dataset.delete(); gdal.GDALDestroyDriverManager(); } /** * shp转换geojson * @param shpFileName * @param geojsonFileName */ public static void shpToGeojson(String shpFileName,String geojsonFileName) { // 注册所有的驱动 ogr.RegisterAll(); // 为了支持中文路径,请添加下面这句代码 gdal.SetConfigOption("GDAL_FILENAME_IS_UTF8","YES"); // 为了使属性表字段支持中文,请添加下面这句 gdal.SetConfigOption("SHAPE_ENCODING",""); //shp文件所在的位置 //String strVectorFile = "D:\\sichuan\\sichuanPointALL.shp"; //打开数据 DataSource ds = ogr.Open(shpFileName,0); if (ds == null) { System.out.println("打开文件失败!" ); return; } System.out.println("打开文件成功!" ); org.gdal.ogr.Driver dv = ogr.GetDriverByName("GeoJSON"); if (dv == null) { System.out.println("打开驱动失败!" ); return; } System.out.println("打开驱动成功!" ); //输出geojson的位置及文件名 //String geojsonFileName = "D:\\data\\sichuan.geojson"; dv.CopyDataSource(ds, geojsonFileName); System.out.println("转换成功!"); } /** * 获取每个点的高程值 * @param fileName_tif */ public static void getElevationFromTif(String fileName_tif) { gdal.AllRegister(); Dataset hDataset = gdal.Open(fileName_tif, gdalconstConstants.GA_ReadOnly); if (hDataset == null) { System.err.println("GDALOpen failed - " + gdal.GetLastErrorNo()); System.err.println(gdal.GetLastErrorMsg()); System.exit(1); } Driver hDriver = hDataset.GetDriver(); System.out.println("Driver: " + hDriver.getShortName() + "/" + hDriver.getLongName()); int iXSize = hDataset.getRasterXSize(); int iYSize = hDataset.getRasterYSize(); System.out.println("Size is " + iXSize + ", " + iYSize); Band band = hDataset.GetRasterBand(1); //这里是DEM数据,所以声明一个int数组来存储,如果是其他数据类型,声明相应的类型即可 int buf[] = new int[iXSize]; for(int i=0; i<50/*iYSize*/; i++) { band.ReadRaster(0, i, iXSize, 1, buf); //读取一行数据 // 下面是输出像元值,为了方便,我只输出了左上角 10×10的范围内的数据 for(int j=0; j<50/*iXSize*/; j++){ System.out.print(buf[j] + ", "); } System.out.println("\n"); } hDataset.delete(); // 可选 gdal.GDALDestroyDriverManager(); }}
执行结果示例:
PS:运行java工程时可能的报错:
1. 工程中只引用了gdal.jar包,没有任何gdal_java的dll
Native library load failed.
java.lang.UnsatisfiedLinkError: no gdaljni in java.library.path
Exception in thread "main" java.lang.UnsatisfiedLinkError: org.gdal.gdal.gdalJNI.AllRegister()V
at org.gdal.gdal.gdalJNI.AllRegister(Native Method)
at org.gdal.gdal.gdal.AllRegister(gdal.java:519)
at com.ysq.gdal.HelloGDAL.getElevationFromTif(HelloGDAL.java:91)
at com.ysq.gdal.HelloGDAL.main(HelloGDAL.java:17)
2. 有引用了gdal.jar包 ,也将releasegdal_java的dll文件拷贝到正确位置,但是缺少GDAL本身的dll(即release-1800-gdal/bin下的众多dll文件)
发表评论
最新留言
关于作者
