通过java代码将sde表里面的矢量数据导入到shapefile文件里面

需要注意的问题是,当表字段的长度大于10,在往shape文件写数据时会报错,可以将字段截取前10位

第一步,根据如下的sql语句找到srtext信息,这个信息是在生成shapefile文件时,设置坐标系的

SELECT st_srid(shape) FROM sde.ele_bil_a ORDER BY objectid asc limit 1

SELECT srtext FROM public.sde_spatial_references where srid=4326

srtext的信息列子如下

GEOGCS["GCS_WGS_1984",DATUM["D_WGS_1984",SPHEROID["WGS_1984",6378137.0,298.257223563]],PRIMEM["Greenwich",0.0],UNIT["Degree",0.0174532925199433]]

引入依赖

<repositories>
    <repository>
        <id>OSGeo-Repository</id>
        <name>OSGeo-Repository</name>
        <url>https://repo.osgeo.org/repository/release</url>
    </repository>
</repositories>
<dependency>
    <groupId>org.geotools</groupId>
    <artifactId>gt-shapefile</artifactId>
    <version>24.0</version>
    <exclusions>
        <exclusion>
            <artifactId>commons-text</artifactId>
            <groupId>org.apache.commons</groupId>
        </exclusion>
    </exclusions>
</dependency>


import org.apache.commons.lang3.StringUtils;
import org.geotools.data.FeatureWriter;
import org.geotools.data.Transaction;
import org.geotools.data.shapefile.ShapefileDataStore;
import org.geotools.data.shapefile.ShapefileDataStoreFactory;
import org.geotools.feature.simple.SimpleFeatureTypeBuilder;
import org.geotools.referencing.CRS;
import org.geotools.referencing.crs.DefaultGeographicCRS;
import org.geotools.referencing.crs.DefaultEngineeringCRS;
import org.locationtech.jts.geom.*;
import org.locationtech.jts.io.WKTReader;
import org.opengis.feature.simple.SimpleFeature;
import org.opengis.feature.simple.SimpleFeatureType;
import org.opengis.referencing.crs.CoordinateReferenceSystem;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.*;
import java.nio.charset.Charset;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;


public class ShapeUtil {

    private static Logger LOG = LoggerFactory.getLogger(ShapeUtil.class);

    /**
     * 生成shape文件
     *
     * @param shpPath 生成shape文件路径(包含文件名称)
     * @param encode  编码
     * @param geoType 图幅类型,Point和Rolygon
     * @param geoms   图幅集合
     */
    public static void write2Shape(String shpPath, String encode, String geoType, List<Geometry> geoms) {
        try {
            //创建shape文件对象
            File file = new File(shpPath);
            Map<String, Serializable> params = new HashMap<>();
            params.put(ShapefileDataStoreFactory.URLP.key, file.toURI().toURL());
            ShapefileDataStore ds = (ShapefileDataStore) new ShapefileDataStoreFactory().createNewDataStore(params);
            //定义图形信息和属性信息
            SimpleFeatureTypeBuilder tb = new SimpleFeatureTypeBuilder();
            tb.setCRS(DefaultGeographicCRS.WGS84);
            tb.setName("shapefile");

            if ("Polygon".equals(geoType)) {
                tb.add("the_geom", Polygon.class);
            } else if ("MultiPolygon".equals(geoType)) {
                tb.add("the_geom", MultiPolygon.class);
            } else if ("Point".equals(geoType)) {
                tb.add("the_geom", Point.class);
            } else if ("MultiPoint".equals(geoType)) {
                tb.add("the_geom", MultiPoint.class);
            } else if ("LineString".equals(geoType)) {
                tb.add("the_geom", LineString.class);
            } else if ("MultiLineString".equals(geoType)) {
                tb.add("the_geom", MultiLineString.class);
            } else {
                throw new Exception("Geometry中没有该类型:" + geoType);
            }

            ds.createSchema(tb.buildFeatureType());
            //设置编码
            Charset charset = Charset.forName(encode);
            ds.setCharset(charset);
            //设置Writer
            FeatureWriter<SimpleFeatureType, SimpleFeature> writer = ds.getFeatureWriter(ds.getTypeNames()[0], Transaction.AUTO_COMMIT);
            for (Geometry geom : geoms) {
                //String type = geom.getGeometryType();

                //写下一条
                SimpleFeature feature = writer.next();

                feature.setAttribute("the_geom", geom);
            }
            writer.write();
            writer.close();
            ds.dispose();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }



    /**
     * 生成shape文件
     *
     * @param shpPath  生成shape文件路径(包含文件名称)
     * @param encode   编码
     * @param geoType  图幅类型,Point和Rolygon
     * @param shpKey   data中图幅的key
     * @param attrKeys 属性key集合
     * @param data     图幅和属性集合
     */
    public static boolean write2Shape(String shpPath, String encode, String geoType, String shpKey, List<String> attrKeys, List<Map<String, Object>> data, String srtext) {
        File file = new File(shpPath);
        Map<String, Serializable> params = new HashMap<>();
        ShapefileDataStore ds = null;
        try {
            if (data == null || data.size() == 0) {
                return false;
            }
            // 根据SRID创建坐标参考系统
            CoordinateReferenceSystem crs = null;
            if(StringUtils.isNotBlank(srtext)){
                try {
                    crs = CRS.parseWKT(srtext);
                } catch (Exception e) {
                    LOG.error("---------crs error...");
                }
            }


            //创建shape文件对象
            params.put(ShapefileDataStoreFactory.URLP.key, file.toURI().toURL());
            ds = (ShapefileDataStore) new ShapefileDataStoreFactory().createNewDataStore(params);

            //定义图形信息和属性信息
            SimpleFeatureTypeBuilder tb = new SimpleFeatureTypeBuilder();
            if(crs != null){
                tb.setCRS(crs);
            }else {
                LOG.info("crs is null...");
                tb.setCRS(DefaultGeographicCRS.WGS84);
            }
            tb.setName("shapefile");

            if ("Polygon".equals(geoType)) {
                tb.add("the_geom", Polygon.class);
            } else if ("MultiPolygon".equals(geoType)) {
                tb.add("the_geom", MultiPolygon.class);
            } else if ("Point".equals(geoType)) {
                tb.add("the_geom", Point.class);
            } else if ("MultiPoint".equals(geoType)) {
                tb.add("the_geom", MultiPoint.class);
            } else if ("LineString".equals(geoType)) {
                tb.add("the_geom", LineString.class);
            } else if ("MultiLineString".equals(geoType)) {
                tb.add("the_geom", MultiLineString.class);
            } else {
                throw new Exception("Geometry中没有该类型:" + geoType);
            }

            for (String field : attrKeys) {
                tb.add(field, String.class);
            }

            ds.createSchema(tb.buildFeatureType());
            //设置编码
            Charset charset = Charset.forName(encode);
            ds.setCharset(charset);
            //设置Writer
            FeatureWriter<SimpleFeatureType, SimpleFeature> writer = ds.getFeatureWriter(ds.getTypeNames()[0], Transaction.AUTO_COMMIT);
            //写入文件信息
            for (int i = 0; i < data.size(); i++) {
                SimpleFeature feature = writer.next();
                Map<String, Object> row = data.get(i);
                if(row.get(shpKey) == null){
                    feature.setAttribute("the_geom", null);
                }else {
                    Geometry geom = getByWKT(row.get(shpKey).toString());
                    feature.setAttribute("the_geom", geom);
                }

                for (String key : row.keySet()) {
                    if (!key.equals(shpKey)) {
                        if (row.get(key) != null) {
                            feature.setAttribute(key, row.get(key).toString());
                        } else {
                            feature.setAttribute(key, "");
                        }
                    }
                }
            }
            writer.write();
            writer.close();
            ds.dispose();
            return true;
            //添加到压缩文件
            //zipShapeFile(shpPath);
        } catch (Exception e) {
            e.printStackTrace();
        }finally {
            if(ds != null){
                ds.dispose();
            }
        }
        return false;
    }

    private static Geometry getByWKT(String wkt){
        try {
            WKTReader reader = new WKTReader();
            Geometry geometry = reader.read(wkt);
            return geometry;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }


    /**
     * 压缩shape文件
     *
     * @param shpPath shape文件路径(包含shape文件名称)
     */
    public static boolean zipShapeFile(String shpPath) {
        InputStream input = null;
        ZipOutputStream zipOut = null;
        try {
            File shpFile = new File(shpPath);
            String shpRoot = shpFile.getParentFile().getPath();
            String shpName = shpFile.getName().substring(0, shpFile.getName().lastIndexOf("."));

            String zipPath = shpRoot + File.separator + shpName + ".zip";
            File zipFile = new File(zipPath);

            zipOut = new ZipOutputStream(new FileOutputStream(zipFile));
            // zip的名称为
            zipOut.setComment(shpName);
            String[] shpFiles = new String[]{
                    shpRoot + File.separator + shpName + ".dbf",
                    shpRoot + File.separator + shpName + ".prj",
                    shpRoot + File.separator + shpName + ".shp",
                    shpRoot + File.separator + shpName + ".shx",
                    shpRoot + File.separator + shpName + ".fix"
            };

            for (int i = 0; i < shpFiles.length; i++) {
                File file = new File(shpFiles[i]);
                input = new FileInputStream(file);
                zipOut.putNextEntry(new ZipEntry(file.getName()));
                int temp = 0;
                while ((temp = input.read()) != -1) {
                    zipOut.write(temp);
                }
                input.close();
            }
            return true;
        } catch (Exception e) {
            LOG.error("---------------error...");
            e.printStackTrace();
        }finally {
            if(input != null){
                try {
                    input.close();
                } catch (IOException e) {
                    throw new RuntimeException(e);
                }
            }
            if(zipOut != null){
                try {
                    zipOut.close();
                } catch (IOException e) {
                    throw new RuntimeException(e);
                }
            }
        }
        return false;
    }

    public static void main(String[] args) {
//        zipShapeFile("C:\\file\\shp\\d35e6134999143009871aeecd52bc4cc\\ELE_BIL_P.shp");
        // 根据SRID创建坐标参考系统
        CoordinateReferenceSystem crs = null;
        String wktString = "GEOGCS[\"GCS_WGS_1984\",DATUM[\"D_WGS_1984\",SPHEROID[\"WGS_1984\",6378137.0,298.257223563]],PRIMEM[\"Greenwich\",0.0],UNIT[\"Degree\",0.0174532925199433]]";
        try {
//            crs = CRS.decode("EPSG:" + 4490);
            crs = CRS.parseWKT(wktString);
            System.out.println("---------------");
        } catch (Exception e) {
            e.printStackTrace();
            // 处理异常,例如无效的SRID
        }

    }
}

调用实例

public String exportShp(PageRequest page) throws ParseException {
        StringBuffer sql = new StringBuffer("select objectid,XZQHDM,XZQHMC,SJXZQHDM,XZQHJB,st_astext(shape) as shape from sde.XZQH");
        Query query = entityManager.createNativeQuery(sql.toString(), Region.class);
        List<Region> list = query.getResultList();
        if(list == null || list.size() <= 0){
            return null;
        }
        List<String> attrKeys = new ArrayList<>();
        attrKeys.add("objectid");
        attrKeys.add("XZQHDM");
        attrKeys.add("XZQHMC");
        attrKeys.add("SJXZQHDM");
        attrKeys.add("XZQHJB");
        attrKeys.add("shape");
        List<Map<String, Object>> data = new ArrayList<>();
        for (Region region : list) {
            Map<String, Object> map = new HashMap<>();
            map.put("objectid", region.getObjectid());
            map.put("XZQHDM", region.getXZQHDM());
            map.put("XZQHMC", region.getXZQHMC());
            map.put("SJXZQHDM", region.getSJXZQHDM());
            map.put("XZQHJB", region.getXZQHJB());
            if(region.getShape() != null){
                Geometry geom = WKTUtil.wktToGeom(region.getShape());
                map.put("shape", geom);
            }else {
                map.put("shape", null);
            }
            data.add(map);
        }
        String uuid = UUIDUtils.getUUID();
        String url =  "C:/files/shp/" + uuid + ".shp";
        ShapeUtil.write2Shape(url, "utf-8", "Polygon", "shape", attrKeys, data);
        ShapeUtil.zipShapeFile(url);
        return  "htp://127.0.0.1/files/" + uuid + ".zip";
    }

如果不知道shape的类型,可以根据这个来判断

if(StringUtils.isNotBlank(wkt)){
                wkt = wkt.toUpperCase();
                if(wkt.contains("MULTIPOINT")){
                    geoType = "MultiPoint";
                }else if(wkt.contains("POINT")){
                    geoType = "Point";
                }else if(wkt.contains("MULTIPOLYGON")){
                    geoType = "MultiPolygon";
                }else if(wkt.contains("MULTILINESTRING")){
                    geoType = "MultiLineString";
                }else if(wkt.contains("LINESTRING")){
                    geoType = "LineString";
                }else if(wkt.contains("POLYGON")){
                    geoType = "Polygon";
                }else {
                    LOG.info(wkt);
                }
            }

  • 6
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值