Browse Source

完善接口

DESKTOP-6LTVLN7\Liumouren 3 tháng trước cách đây
mục cha
commit
fb5d661481

+ 5 - 0
pom.xml

@@ -31,6 +31,11 @@
         <java.version>17</java.version>
     </properties>
     <dependencies>
+        <dependency>
+            <groupId>com.fasterxml.jackson.core</groupId>
+            <artifactId>jackson-databind</artifactId>
+            <version>2.12.3</version>
+        </dependency>
         <dependency>
             <groupId>com.alibaba</groupId>
             <artifactId>fastjson</artifactId>

+ 2 - 2
src/main/java/com/example/poiaddr/PoiAddrApplication.java

@@ -2,10 +2,10 @@ package com.example.poiaddr;
 
 import org.springframework.boot.SpringApplication;
 import org.springframework.boot.autoconfigure.SpringBootApplication;
-
+import org.springframework.scheduling.annotation.EnableScheduling;
 @SpringBootApplication
+@EnableScheduling
 public class PoiAddrApplication {
-
     public static void main(String[] args) {
         SpringApplication.run(PoiAddrApplication.class, args);
     }

+ 131 - 172
src/main/java/com/example/poiaddr/controller/PoiAddressController.java

@@ -1,15 +1,12 @@
 package com.example.poiaddr.controller;
 
+import com.example.poiaddr.entity.FileDataDto;
 import com.example.poiaddr.entity.PoiAddress;
 import com.example.poiaddr.service.PoiAddressService;
-import com.example.poiaddr.util.ExcelReaderUtils;
+import com.example.poiaddr.util.CoordTransform;
 import com.example.poiaddr.util.RequestUtils;
-import com.fasterxml.jackson.databind.ObjectMapper;
+import com.example.poiaddr.util.fileTools.ReadFileData;
 import lombok.extern.slf4j.Slf4j;
-import org.apache.commons.lang3.StringUtils;
-import org.json.simple.JSONArray;
-import org.json.simple.JSONObject;
-import org.json.simple.parser.JSONParser;
 import org.locationtech.jts.geom.Coordinate;
 import org.locationtech.jts.geom.GeometryFactory;
 import org.locationtech.jts.geom.Point;
@@ -23,8 +20,6 @@ import javax.annotation.Resource;
 import javax.servlet.http.HttpServletResponse;
 import java.io.*;
 import java.util.*;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
 
 @Slf4j
 @Validated
@@ -68,165 +63,6 @@ public class PoiAddressController {
         return RequestUtils.request(address);
     }
 
-    //    创建一个方法能读取xlsx文件数据并返回List<Map>集合
-//    创建一个setList集合判断文档中的数据不能地址重复
-//    然后根据这个list集合创建多线程请求数据并插入到数据库中
-//    filePath:C:\Users\Liumouren\Desktop\临时文件\元以科技\青浦\青浦城建所\poiAddr\doc\
-    @GetMapping(value = "/test")
-    public Object test() {
-//        try {
-////          根据文件路径得到下面的所有文件集合
-//            List<File> fileList = ExcelReaderUtils.listFilesInDirectory("C:\\Users\\Liumouren\\Desktop\\临时文件\\元以科技\\青浦\\青浦城建所\\poiAddr\\doc\\");
-////          根据文件集合得到
-//            List<Map<String, String>> errorData = new ArrayList<>();
-//            Set<String> addressSet = new HashSet<>();
-//            for (File fileItem : fileList) {
-//                if (fileItem.getPath().contains(".xlsx") && fileItem.getPath().contains("marge_excel_uuid")) {
-//                    List<Map<String, Object>> dataList = ExcelReaderUtils.readExcel(fileItem.getPath());
-//                    for (Map<String, Object> map : dataList) {
-//                        if (map.containsKey("详细地址")) {
-//                            addressSet.add(map.get("详细地址").toString());
-//                        }
-//                    }
-//                }
-//            }
-//
-////            得到geojson中的所有的地址名称
-////            Set<String> addressSet = JacksonExample.getAddressList();
-////          测试请求结果
-//            ArrayList<JSONObject> resultList = new ArrayList<>();
-//            ArrayList<String> addressList = new ArrayList<>();
-//            for (String addrStr : addressSet) {
-//                String addrStr2 = StringUtils.deleteWhitespace(addrStr);
-//                if (addrStr2.length() > 5) {
-//                    addressList.add(addrStr2);
-//                } else {
-//                    Map<String, String> error = new HashMap<>();
-//                    error.put("错误地址:", addrStr2);
-//                    error.put("msg", "地址长度不规范");
-//                    errorData.add(error);
-//                }
-//            }
-//            int threadCount = 10; // 设置线程数量
-//            ExecutorService executorService = Executors.newFixedThreadPool(threadCount);
-//            // 将集合拆分成多个子任务
-//            int partSize = addressList.size() / threadCount;
-//            for (int i = 0; i < threadCount; i++) {
-//                int startIndex = i * partSize;
-//                int endIndex = (i == threadCount - 1) ? addressList.size() : (i + 1) * partSize;
-//                List<String> subList = addressList.subList(startIndex, endIndex);
-//                // 提交Runnable任务到线程池
-//                Runnable runnable = () -> {
-//                    for (String addrStr2 : subList) {
-//                        String resultStr = RequestUtils.request(addrStr2);
-//                        if (resultStr != null && resultStr.contains("result")) {
-//                            JSONParser jsonParser = new JSONParser();
-//                            try {
-//                                JSONObject resultObject = (JSONObject) jsonParser.parse(resultStr);
-//                                JSONArray result = (JSONArray) resultObject.get("result");
-//                                if (result.size() > 0) {
-//                                    System.out.println(addrStr2 + "------解析成功数据:" + jsonParser.parse(resultStr));
-//                                    resultList.add(resultObject);
-//                                } else {
-//                                    System.err.println(addrStr2 + "------解析失败数据:" + resultStr);
-//                                    Map<String, String> error = new HashMap<>();
-//                                    error.put("错误地址:", addrStr2);
-//                                    error.put("msg", "地名地址解析失败");
-//                                    errorData.add(error);
-//                                }
-//                            } catch (Exception e) {
-//                                System.err.println(addrStr2 + "------解析失败数据:" + resultStr);
-//                                Map<String, String> error = new HashMap<>();
-//                                error.put("错误地址:", addrStr2);
-//                                error.put("msg", "地名地址解析失败");
-//                                errorData.add(error);
-//                            }
-//                        }
-//                    }
-//                };
-//                executorService.submit(runnable);
-//            }
-//
-//            // 关闭线程池(不再接受新任务,但会等待已提交任务完成)
-//            executorService.shutdown();
-//            // 等待所有任务完成
-//            try {
-//                while (!executorService.isTerminated()) {
-//                    Thread.sleep(100);
-//                }
-//                System.out.println("所有任务已完成");
-//                for (JSONObject resultItem : resultList) {
-//                    JSONArray result = (JSONArray) resultItem.get("result");
-//                    JSONObject resultData = (JSONObject) result.get(0);
-//                    JSONObject extData = (JSONObject) resultData.get("ext_data");
-//                    PoiAddress poiAddress = new PoiAddress();
-//                    poiAddress.setUuid(UUID.randomUUID().toString());
-//                    poiAddress.setAddress(extData.get("address").toString());
-//                    poiAddress.setAddressCode(extData.get("address_code").toString());
-//                    poiAddress.setLocation(resultData.get("location").toString());
-//                    poiAddress.setBuilding(extData.get("building").toString());
-//                    poiAddress.setAttachInfo(extData.get("attach_info").toString());
-//                    poiAddress.setBuildingAlias(extData.get("building_alias").toString());
-//                    poiAddress.setCoordAdcode(extData.get("coord_adcode").toString());
-//                    poiAddress.setDataOperation(extData.get("data_operation").toString());
-//                    poiAddress.setDataSource(extData.get("data_source").toString());
-//                    poiAddress.setDataOperationCheck(extData.get("data_operation_check").toString());
-//                    poiAddress.setFloor(extData.get("floor").toString());
-//                    poiAddress.setHistoryData(extData.get("history_data").toString());
-//                    poiAddress.setManualMark(extData.get("manual_mark").toString());
-//                    poiAddress.setName1(extData.get("name1").toString());
-//                    poiAddress.setNo1(extData.get("no1").toString());
-//                    poiAddress.setNo2(extData.get("no2").toString());
-//                    poiAddress.setNo3(extData.get("no3").toString());
-//                    poiAddress.setNo4(extData.get("no4").toString());
-//                    poiAddress.setOperationRemark(extData.get("operation_remark").toString());
-//                    poiAddress.setOperationRemarkCheck(extData.get("operation_remark_check").toString());
-//                    poiAddress.setParentAddressCode(extData.get("parent_address_code").toString());
-//                    poiAddress.setPointB(extData.get("point_b").toString());
-//                    poiAddress.setPointL(extData.get("point_l").toString());
-//                    poiAddress.setPointX(extData.get("point_x").toString());
-//                    poiAddress.setPointY(extData.get("point_y").toString());
-//                    poiAddress.setPoiString(extData.get("poi_string").toString());
-//                    poiAddress.setRegionJd(extData.get("region_jd").toString());
-//                    poiAddress.setRegionJw(extData.get("region_jw").toString());
-//                    poiAddress.setRegionQx(extData.get("region_jw").toString());
-//                    poiAddress.setRegionSs(extData.get("region_ss").toString());
-//                    poiAddress.setRegionXq(extData.get("region_xq").toString());
-//                    poiAddress.setRegionXqAlias(extData.get("region_xq_alias").toString());
-//                    poiAddress.setRelationExtraAlias(extData.get("relation_extra_alias").toString());
-//                    poiAddress.setRelationSnMark(extData.get("relation_sn_mark").toString());
-//                    poiAddress.setRoomNo(extData.get("room_no").toString());
-//                    poiAddress.setRoomNoAlias(extData.get("room_no_alias").toString());
-//                    poiAddress.setSemanticsSource(extData.get("semantics_source").toString());
-//                    poiAddress.setSourceAddress(extData.get("source_address").toString());
-//                    poiAddress.setSpecificationUpdateMark(extData.get("specification_update_mark").toString());
-//                    poiAddress.setSubRegionXq(extData.get("sub_region_xq").toString());
-//                    poiAddress.setUnit(extData.get("unit").toString());
-//                    poiAddress.setUnitAlias(extData.get("unit_alias").toString());
-//                    poiAddressService.save(poiAddress);
-//                }
-////              将异常的数据保存为一个json文件
-//                if (errorData.size() > 0) {
-//                    ObjectMapper objectMapper = new ObjectMapper();
-//                    String outputFilePath = "C:\\Users\\Liumouren\\Desktop\\errorAddressData.json"; // 输出文件路径,可按需修改
-//                    FileOutputStream fos = new FileOutputStream(new File(outputFilePath));
-//                    objectMapper.writeValue(fos, errorData);
-//                    fos.close();
-//                }
-//                System.out.println("解析文件得到的地址个数:" + addressSet.size() + ",异常的有" + errorData.size());
-//                return "解析文件得到的地址个数:" + addressSet.size() + ",异常的有" + errorData.size();
-//            } catch (InterruptedException e) {
-//                e.printStackTrace();
-//                return e;
-//            }
-//        } catch (IOException e) {
-//            e.printStackTrace();
-//            return e;
-//        }
-        return "test";
-    }
-
-
     /**
      * 地名查询任务接口
      * * 参数:
@@ -234,12 +70,12 @@ public class PoiAddressController {
      * *** file: xlsx、csv、geojson、shape
      * *** addrColNames: 地名地址字段名称数组,依次查询
      * ** 非必填:
-     * *** inCoordinate: 输入坐标系
+     * *** inCoordinate: 输入坐标系(默认为wgs84)
      * *** latLonColName: 经纬度字段名称,如果长度为一,经纬度字段分隔符为必填
      * *** latLonSplitStr: 经纬度字段分隔符
      * *** matchingDistance: 匹配距离,如果不为空,经纬度字段名称不能为空
      * *** outCoordinate: 输出坐标系(默认为wgs84)
-     * *** matchingLevel: 匹配等级,详情见xmind文件
+     * *** matchingLevel: 匹配等级,详情见xmind文件【1、2、3、4、0】
      * *** regionalJudgment: 区域判断,geojson、shape文件[前端可以内置一些常用的区域文件,通过下拉框的方式进行选择]
      * *** outFileType: 输出文件类型【xlsx、csv、geojson、shape】
      *
@@ -251,13 +87,136 @@ public class PoiAddressController {
                                 @RequestParam(name = "inCoordinate", required = false) String inCoordinate,
                                 @RequestParam(name = "latLonColName", required = false) String latLonColName,
                                 @RequestParam(name = "latLonSplitStr", required = false) String latLonSplitStr,
-                                @RequestParam(name = "matchingDistance", required = false) String matchingDistance,
+                                @RequestParam(name = "matchingDistance", required = false) Long matchingDistance,
                                 @RequestParam(name = "outCoordinate", required = false) String outCoordinate,
                                 @RequestParam(name = "matchingLevel", required = false) String matchingLevel,
                                 @RequestParam(name = "regionalJudgment", required = false) MultipartFile regionalJudgment,
                                 @RequestParam(name = "outFileType", required = false) String outFileType) throws IOException {
-        if ((file != null && !file.isEmpty()) || (addrColNames != null && !addrColNames.isEmpty())) {
-            return null;
+//            参数合法性判断
+        if ((file != null && !file.isEmpty()) && (addrColNames != null && !addrColNames.isEmpty())) {
+//          搜索地址key
+            String addr1Key = "";
+            String addr2Key = "";
+//          参考经纬度key
+            String latKey = "";
+            String lonKey = "";
+            String latLonKey = "";
+            String SplitStr = "";
+//          多地址的形式
+            if (addrColNames.contains(",")) {
+                String[] addrs = addrColNames.split(",");
+                if (addrs.length > 2) {
+                    return "最多支持两个地址列查询,请检查addrColNames参数!";
+                }
+                addr1Key = addrs[0];
+                addr2Key = addrs[1];
+            } else {
+                addr1Key = addrColNames;
+            }
+
+            if (matchingLevel == null || matchingLevel.isEmpty()) {
+                return "请传入搜索等级参数,matchingLevel参数不能为空!";
+            }
+//          匹配距离参数合法性判断
+            if (matchingDistance != null) {
+                if (latLonColName == null || latLonColName.isEmpty()) {
+                    return "当匹配距离参数不为空时,必须传入经纬度参数!";
+                }
+            }
+//          经纬度合法性判断
+            if (latLonColName != null) {
+//              两个key
+                if (latLonColName.contains(",")) {
+                    String[] latLons = latLonColName.split(",");
+                    latKey = latLons[0];
+                    lonKey = latLons[1];
+                } else if (latLonSplitStr != null && !latLonSplitStr.isEmpty()) {
+//                    单个key分割,必须要分割符参数
+                    latLonKey = latLonColName;
+                    SplitStr = latLonSplitStr;
+                } else {
+                    return "经纬度列名解析失败,请传入经度和纬度的列名以逗号分割或传入经纬度列名和分隔符参数!";
+                }
+            }
+//          封装解析文件的参数
+//          TODO 文件数据解析
+            assert file != null;
+            List<FileDataDto> fileDataDtoList = ReadFileData.ReadMultipartFile(file);
+//          TODO 补充FileDataDto中的搜索条件参数
+            for (FileDataDto fileDataDto : fileDataDtoList) {
+//              搜索等级
+                fileDataDto.setMatchingLevel(matchingLevel);
+//                set地名地址搜索字段
+                Map<String, Object> properties = fileDataDto.getProperties();
+                if (addr1Key != null && !addr1Key.isEmpty()) {
+                    String address = "上海市青浦区" + properties.getOrDefault(addr1Key, "").toString().replace("青浦区", "").replace(
+                    "青浦", "").replace("上海市","").replace("上海","").replace("/弄","").replace("/号","").replace("弄","").replace("/幢","").replace("/室"," ").replace("(号楼) "," ");
+                    fileDataDto.setAddr1(address);
+                }
+                if (addr2Key != null && !addr2Key.isEmpty()) {
+                    String address = "上海市青浦区" + properties.getOrDefault(addr2Key, "").toString().replace("青浦区", "").replace(
+                            "青浦", "").replace("上海市","").replace("上海","").replace("/弄","").replace("/号","").replace("弄","").replace("/幢","").replace("/室"," ").replace("(号楼) "," ");
+                    fileDataDto.setAddr2(address);
+                }
+//              判断是否有参考经纬度字段
+                if (latKey != null && !latKey.isEmpty() && lonKey != null && !lonKey.isEmpty() && properties.get(latKey) != null && properties.get(lonKey) != null) {
+                    String latStr = properties.get(latKey).toString();
+                    String lonStr = properties.get(lonKey).toString();
+                    fileDataDto.setLat(Double.valueOf(latStr));
+                    fileDataDto.setLon(Double.valueOf(lonStr));
+                } else if (!latLonKey.isEmpty() && !SplitStr.isEmpty()) {
+                    String[] latLonKeys = latLonKey.split(SplitStr);
+                    if (properties.get(latLonKeys[0]) != null && properties.get(latLonKeys[1]) != null) {
+                        String latStr = properties.get(latLonKeys[0]).toString();
+                        String lonStr = properties.get(latLonKeys[1]).toString();
+                        fileDataDto.setLat(Double.valueOf(latStr));
+                        fileDataDto.setLon(Double.valueOf(lonStr));
+                    }
+                }
+            }
+//          TODO 地名查询
+//          TODO 转换坐标(根据输入坐标系将参考坐标统一转换成wgs84)
+            ArrayList<String> selectOptions = new ArrayList<>();
+//            {"WGS84(国际通用)", "GCJ02(高德、QQ地图)", "BD09(百度地图)", "上海2000坐标系"}
+            selectOptions.add("WGS84");
+            selectOptions.add("GCJ02");
+            selectOptions.add("BD09");
+            selectOptions.add("SH2000");
+            if(inCoordinate != null && !inCoordinate.isEmpty()){
+                if (!selectOptions.contains(inCoordinate)) {
+                    return "请传入正确的坐标系名称!可选坐标系名称:WGS84,GCJ02,BD09,SH2000";
+                }
+            }else{
+                inCoordinate = "WGS84";
+            }
+            for(FileDataDto fileDataDto:fileDataDtoList){
+                if(fileDataDto.getLat() != null && fileDataDto.getLon() != null){
+                    double[] lonLat = com.example.poiaddr.util.Coordinate.transformationCoordinateByCoordinate(fileDataDto.getLat(),fileDataDto.getLon(),inCoordinate,outCoordinate);
+                    fileDataDto.setLat(lonLat[1]);
+                    fileDataDto.setLon(lonLat[0]);
+                }
+                //          TODO 距离计算
+                if(matchingDistance != null){
+                    if(fileDataDto.getResultLat() != null && fileDataDto.getResultLon() != null && fileDataDto.getLat() != null && fileDataDto.getLon() != null){
+                        double distance = com.example.poiaddr.util.Coordinate.calculateDistance(fileDataDto.getResultLat(),fileDataDto.getResultLon(),fileDataDto.getLat(),fileDataDto.getLon());
+                        fileDataDto.setMatchingDistance(distance);
+                        double matchingDistanceDb = Double.parseDouble(matchingDistance.toString());
+                        if(distance < matchingDistanceDb){
+                            fileDataDto.setLtMatchingDistance("是");
+                        }else{
+                            fileDataDto.setLtMatchingDistance("否");
+                        }
+                    }
+                }
+                //          TODO 区域判断
+                if(regionalJudgment != null && !regionalJudgment.isEmpty()){
+//                  解析geojson文件得到区域
+
+                }
+            }
+//          TODO 转换坐标
+//          TODO 结果输出
+            return "文件解析完成,共" + fileDataDtoList.size() + "条数据!";
         } else {
             return "file或addrColName不能为空!";
         }

+ 21 - 0
src/main/java/com/example/poiaddr/entity/FeatureDiy.java

@@ -0,0 +1,21 @@
+package com.example.poiaddr.entity;
+import com.fasterxml.jackson.annotation.JsonProperty;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.io.Serializable;
+import java.util.Map;
+
+// 代表 GeoJSON 的 Feature
+@AllArgsConstructor
+@NoArgsConstructor
+@Data
+public class FeatureDiy implements Serializable {
+    @JsonProperty("type")
+    private String type;
+    @JsonProperty("geometry")
+    private GeometryDiy geometry;
+    @JsonProperty("properties")
+    private Map<String,Object> properties;
+}

+ 42 - 0
src/main/java/com/example/poiaddr/entity/FileDataDto.java

@@ -0,0 +1,42 @@
+package com.example.poiaddr.entity;
+
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+import java.io.Serializable;
+import java.util.Map;
+
+@AllArgsConstructor
+@NoArgsConstructor
+@Data
+/**
+ * 地名地址查询返回实体类
+ * 文件名编码格式result[_匹配等级][_匹配距离][_区域名称][_坐标系].[文件类型]
+ */
+public class FileDataDto implements Serializable {
+//  查询地址1
+    private String addr1;
+//  查询地址2
+    private String addr2;
+//  查询结果经度(默认返回的都是wgs84)
+    private Double resultLat;
+//  查询结果纬度(默认返回的都是wgs84)
+    private Double resultLon;
+//  参考经度(可能为空)
+    private Double lat;
+//  参考纬度(可能为空)
+    private Double lon;
+//  匹配等级
+    private String matchingLevel;
+//  匹配距离(可能为空)
+    private double matchingDistance;
+//  是否小于匹配距离(可能为空)
+    private String ltMatchingDistance;
+//  是否在区域内(可能为空)
+    private String inTheArea;
+//  geojson geometry
+    private GeometryDiy geometry;
+//  所有属性
+    private Map<String,Object> properties;
+}

+ 19 - 0
src/main/java/com/example/poiaddr/entity/GeometryDiy.java

@@ -0,0 +1,19 @@
+package com.example.poiaddr.entity;
+
+import com.fasterxml.jackson.annotation.JsonProperty;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.io.Serializable;
+import java.util.List;
+
+@AllArgsConstructor
+@NoArgsConstructor
+@Data
+public class GeometryDiy implements Serializable {
+    @JsonProperty("type")
+    private String type;
+    @JsonProperty("coordinates")
+    private List<Object> coordinates;
+}

+ 1 - 1
src/main/java/com/example/poiaddr/util/CoordTransform.java

@@ -273,7 +273,7 @@ public class CoordTransform {
         double dLon = lon2Rad - lon1Rad;
         double a = Math.pow(Math.sin(dLat / 2), 2) + Math.cos(lat1Rad) * Math.cos(lat2Rad) * Math.pow(Math.sin(dLon / 2), 2);
         double c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
-        double distance = RADIUS * c;
+        double distance = 6378245.0 * c;
 
         return distance;
     }

+ 84 - 0
src/main/java/com/example/poiaddr/util/Coordinate.java

@@ -343,4 +343,88 @@ public class Coordinate {
         }
     }
 
+//  根据输入和输出坐标系转换坐标
+    public static double[] transformationCoordinateByCoordinate(Double lat,Double lon, String inCoordinate,String outCoordinate){
+        double[] lonLat = new double[0];
+        if ("WGS84".equals(inCoordinate)) {
+            switch (outCoordinate) {
+                case "GCJ02":
+                    lonLat = wgs84_to_gcj02(lon, lat);
+                    break;
+                case "BD09":
+                    lonLat = wgs84_to_bd09(lon, lat);
+                    break;
+                case "SH2000":
+                    lonLat = wgs84_to_shcj(lon, lat);
+                    break;
+            }
+        } else if ("GCJ02".equals(inCoordinate)) {
+            switch (outCoordinate) {
+                case "WGS84":
+                    lonLat = gcj02_to_wgs84(lon, lat);
+                    break;
+                case "BD09":
+                    lonLat = gcj02_to_bd09(lon, lat);
+                    break;
+                case "SH2000":
+                    lonLat = gcj02_to_shcj(lon, lat);
+                    break;
+            }
+        } else if ("BD09".equals(inCoordinate)) {
+            switch (outCoordinate) {
+                case "WGS84":
+                    lonLat = bd09_to_wgs84(lon, lat);
+                    break;
+                case "GCJ02":
+                    lonLat = bd09_to_gcj02(lon, lat);
+                    break;
+                case "SH2000":
+                    double[] lonLat2 = bd09_to_wgs84(lon, lat);
+                    lonLat = wgs84_to_shcj(lonLat2[0], lonLat2[1]);
+                    break;
+            }
+        } else if ("SH2000".equals(inCoordinate)) {
+            switch (outCoordinate) {
+                case "WGS84":
+                    lonLat = shcj_to_wgs84(lon, lat);
+                    break;
+                case "BD09":
+                    double[] lonLat2 = shcj_to_wgs84(lon, lat);
+                    lonLat = wgs84_to_bd09(lonLat2[0], lonLat2[1]);
+                    break;
+                case "GCJ02":
+                    lonLat = shcj_to_gcj02(lon, lat);
+                    break;
+            }
+        }
+        return lonLat;
+    }
+
+    /***
+     *  计算两个经纬度之间的距离,返回单位米
+     * @param lat1
+     * @param lon1
+     * @param lat2
+     * @param lon2
+     * @return
+     */
+    public static double calculateDistance(double lat1, double lon1, double lat2, double lon2) {
+        // 将经纬度转换为弧度
+        double lat1Rad = Math.toRadians(lat1);
+        double lon1Rad = Math.toRadians(lon1);
+        double lat2Rad = Math.toRadians(lat2);
+        double lon2Rad = Math.toRadians(lon2);
+
+//        // 地球半径(单位:千米)
+//        double earthRadius = 6371.0;
+
+        // Haversine公式计算两点之间的距离
+        double dLat = lat2Rad - lat1Rad;
+        double dLon = lon2Rad - lon1Rad;
+        double a = Math.pow(Math.sin(dLat / 2), 2) + Math.cos(lat1Rad) * Math.cos(lat2Rad) * Math.pow(Math.sin(dLon / 2), 2);
+        double c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
+        double distance = 6378245.0 * c;
+
+        return distance;
+    }
 }

+ 10 - 32
src/main/java/com/example/poiaddr/util/ExcelReaderUtils.java

@@ -135,7 +135,7 @@ public class ExcelReaderUtils {
         Sheet sheet = workbook.getSheetAt(0);
 
         int totalRows = sheet.getLastRowNum() + 1;
-        int fileCount = (totalRows / rowsPerFile) + (totalRows % rowsPerFile == 0? 0 : 1);
+        int fileCount = (totalRows / rowsPerFile) + (totalRows % rowsPerFile == 0 ? 0 : 1);
 
         for (int i = 0; i < fileCount; i++) {
             Workbook newWorkbook = new XSSFWorkbook();
@@ -146,11 +146,11 @@ public class ExcelReaderUtils {
             for (int rowIndex = startRow; rowIndex < endRow; rowIndex++) {
                 Row sourceRow = sheet.getRow(rowIndex);
                 Row newRow = newSheet.createRow(rowIndex - startRow);
-                if (sourceRow!= null) {
+                if (sourceRow != null) {
                     for (int cellIndex = 0; cellIndex < sourceRow.getLastCellNum(); cellIndex++) {
                         Cell sourceCell = sourceRow.getCell(cellIndex);
                         Cell newCell = newRow.createCell(cellIndex);
-                        if (sourceCell!= null) {
+                        if (sourceCell != null) {
                             switch (sourceCell.getCellType()) {
                                 case STRING:
                                     newCell.setCellValue(sourceCell.getStringCellValue());
@@ -187,7 +187,7 @@ public class ExcelReaderUtils {
         return baseName + "_part_" + (index + 1) + extension;
     }
 
-    private static Map<String, String>  updateTableHeader() {
+    private static Map<String, String> updateTableHeader() {
         Map<String, String> table1colToName = new HashMap<>();
         table1colToName.put("ID", "序列号");
         table1colToName.put("TASKID", "任务编号");
@@ -281,6 +281,7 @@ public class ExcelReaderUtils {
         table1colToName.put("STATUSNAME", "状态名");
         return table1colToName;
     }
+
     private static String getCellValueAsString(Cell cell) {
         switch (cell.getCellType()) {
             case STRING:
@@ -307,7 +308,7 @@ public class ExcelReaderUtils {
     /**
      * 替换表头
      */
-    private static void ModifyExcelHeaderJExcelApi(){
+    private static void ModifyExcelHeaderJExcelApi() {
         try {
             // 读取现有的Excel文件
             FileInputStream file = new FileInputStream("C:\\Users\\Liumouren\\Desktop\\临时文件\\元以科技\\青浦\\青浦城建所\\poiAddr\\doc\\tableHeader.xlsx");
@@ -318,11 +319,11 @@ public class ExcelReaderUtils {
                 Sheet sheet = workbook.getSheetAt(sheetIndex);
                 // 获取表头行(假设第一行是表头)
                 Row headerRow = sheet.getRow(0);
-                if (headerRow!= null) {
+                if (headerRow != null) {
                     // 遍历每个表头单元格进行替换
                     // 遍历表头行中的每个单元格
                     for (Cell cell : headerRow) {
-                        if (cell!= null) {
+                        if (cell != null) {
                             String oldHeaderValue = getCellValueAsString(cell);
                             if (table1colToName.containsKey(oldHeaderValue)) {
                                 cell.setCellValue(table1colToName.get(oldHeaderValue));
@@ -429,14 +430,11 @@ public class ExcelReaderUtils {
     }
 
 
-    public static void main(String[] args) {
+    /*public static void main(String[] args) {
 //        根据Map字段修改表头
 //        ModifyExcelHeaderJExcelApi();
-
         //          根据文件路径得到下面的所有文件集合
         List<File> fileList = listFilesInDirectory("C:\\Users\\Liumouren\\Desktop\\临时文件\\元以科技\\青浦\\青浦城建所\\poiAddr\\doc\\");
-//          根据文件集合得到
-//        Set<String> addressSet = new HashSet<>();
 //            TODO 所有文件加入
         int tagIndex = 0;
         for (File fileItem : fileList) {
@@ -448,25 +446,5 @@ public class ExcelReaderUtils {
             }
         }
         System.exit(0);
-/*
-//          测试请求结果
-        ArrayList<String> resultList = new ArrayList<>();
-        ArrayList<String> errorResultList = new ArrayList<>();
-        for (String addrStr : addressSet) {
-            String resultStr = RequestUtils.request(StringUtils.deleteWhitespace(addrStr));
-            if (resultStr != null && resultStr.contains("result")) {
-                JSONParser jsonParser = new JSONParser();
-                try {
-//                        System.out.println(addrStr + "------解析成功数据:" + jsonParser.parse(resultStr));
-                    resultList.add(resultStr);
-                } catch (Exception e) {
-//                        System.err.println(addrStr + "------解析失败数据:" + resultStr);
-                    errorResultList.add(addrStr);
-                }
-            }
-        }
-        System.out.println("总地址个数:" + addressSet.size());
-        System.out.println("解析成功的地址个数:" + resultList.size());
-        System.out.println("解析失败的地址个数:" + errorResultList.size());*/
-    }
+    }*/
 }

+ 170 - 0
src/main/java/com/example/poiaddr/util/fileTools/ReadFileData.java

@@ -0,0 +1,170 @@
+package com.example.poiaddr.util.fileTools;
+
+import com.example.poiaddr.entity.FeatureDiy;
+import com.example.poiaddr.entity.FileDataDto;
+import com.fasterxml.jackson.core.type.TypeReference;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import com.opencsv.CSVReader;
+import com.opencsv.exceptions.CsvException;
+import org.apache.poi.ss.usermodel.*;
+import org.apache.poi.util.IOUtils;
+import org.springframework.web.multipart.MultipartFile;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileReader;
+import java.io.IOException;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.nio.file.StandardCopyOption;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * 文件内容解析
+ */
+public class ReadFileData {
+//    文件内容解析
+    public static List<FileDataDto> ReadMultipartFile(MultipartFile multipartFile) throws IOException {
+        List<FileDataDto> fileDataDtoList = new ArrayList<>();
+//      首先判断文件类型,走不同的解析方法
+        String fileName = multipartFile.getOriginalFilename();
+        assert fileName != null;
+        String extension = fileName.substring(fileName.lastIndexOf(".") + 1);
+        extension = extension.toLowerCase();
+        // 创建临时文件
+        File file = convert(multipartFile);
+        if ("geojson".equals(extension) || "json".equals(extension)) {
+            fileDataDtoList = readGeojson(file);
+        } else if ("csv".equals(extension)) {
+            fileDataDtoList = readCsv(file);
+        } else if ("xlsx".equals(extension) || "xls".equals(extension)) {
+            fileDataDtoList = readExcel(file);
+        }
+        return fileDataDtoList;
+    }
+
+    public static List<FileDataDto> readGeojson(File file) throws IOException {
+        List<FileDataDto> resultList = new ArrayList<>();
+        ObjectMapper mapper = new ObjectMapper();
+        List<FeatureDiy> features = mapper.readValue(file, new TypeReference<>() {});
+        for(FeatureDiy featureDiy:features){
+            FileDataDto fileDataDto = new FileDataDto();
+            fileDataDto.setGeometry(featureDiy.getGeometry());
+            fileDataDto.setProperties(featureDiy.getProperties());
+            resultList.add(fileDataDto);
+        }
+        return resultList;
+    }
+
+//    csv文件内容解析
+    public static List<FileDataDto> readCsv(File file){
+        List<FileDataDto> resultList = new ArrayList<>();
+        try {
+            // 读取CSV文件
+            CSVReader reader = new CSVReader(new FileReader(file));
+            List<String[]> csvData = reader.readAll();
+            reader.close();
+            String[] headers = new String[]{};
+            int index = 0;
+            for (String[] row : csvData) {
+                int rowSize = row.length;
+                if(index == 0){
+                    headers = new String[rowSize];
+                    for (int i = 0; i < rowSize; i++) {
+                        headers[i] = row[i];
+                    }
+                }else{
+                    FileDataDto fileDataDto= new FileDataDto();
+                    Map<String,Object> colData = new HashMap<>();
+                    for (int i = 0; i < rowSize; i++) {
+                        colData.put(headers[i],row[i]);
+                    }
+                    fileDataDto.setProperties(colData);
+                    resultList.add(fileDataDto);
+                }
+                index++;
+            }
+        } catch (IOException | CsvException e) {
+            e.printStackTrace();
+        }
+        return resultList;
+    }
+
+    //    xlsx文件内容读取
+    public static List<FileDataDto> readExcel(File file) throws IOException {
+        List<FileDataDto> resultList = new ArrayList<>();
+        FileInputStream fis = new FileInputStream(file);
+        IOUtils.setByteArrayMaxOverride(400000000);
+        // 创建工作簿对象,用于代表整个Excel文件
+        Workbook workbook = WorkbookFactory.create(fis);
+        // 这里我们默认读取第一个工作表,如果需要读取指定名称或者索引的工作表可以进行相应修改
+        Sheet sheet = workbook.getSheetAt(0);
+        // 获取表头行
+        Row headerRow = sheet.getRow(0);
+        int headerSize = headerRow.getLastCellNum();
+
+        // 遍历数据行(从第二行开始,第一行是表头)
+        for (int rowIndex = 1; rowIndex <= sheet.getLastRowNum(); rowIndex++) {
+            FileDataDto fileDataDto = new FileDataDto();
+            Row currentRow = sheet.getRow(rowIndex);
+            Map<String, Object> rowMap = new HashMap<>();
+            for (int cellIndex = 0; cellIndex < headerSize; cellIndex++) {
+                Cell headerCell = headerRow.getCell(cellIndex);
+                Cell currentCell = currentRow.getCell(cellIndex);
+                String headerValue = getCellValue(headerCell).toString();
+                Object currentValue = getCellValue(currentCell);
+                rowMap.put(headerValue, currentValue);
+            }
+            fileDataDto.setProperties(rowMap);
+            resultList.add(fileDataDto);
+        }
+
+        workbook.close();
+        fis.close();
+        return resultList;
+    }
+
+//    xlsx行内数据解析
+    private static Object getCellValue(Cell cell) {
+        if (cell == null) {
+            return null;
+        }
+        CellType cellType = cell.getCellType();
+        switch (cellType) {
+            case STRING:
+                return cell.getStringCellValue();
+            case NUMERIC:
+                if (DateUtil.isCellDateFormatted(cell)) {
+                    return cell.getDateCellValue();
+                } else {
+                    return cell.getNumericCellValue();
+                }
+            case BOOLEAN:
+                return cell.getBooleanCellValue();
+            case FORMULA:
+                return cell.getCellFormula();
+            default:
+                return null;
+        }
+    }
+
+//    文件格式转换
+    public static File convert(MultipartFile multipartFile) throws IOException {
+        // 获取原始文件名
+        String originalFilename = multipartFile.getOriginalFilename();
+        // 获取文件后缀
+        String fileExtension = originalFilename.substring(originalFilename.lastIndexOf("."));
+        // 创建文件对象
+        File convFile = File.createTempFile("temp", fileExtension);
+        // 将 MultipartFile 转换为 Path
+        Path path = Paths.get(convFile.getAbsolutePath());
+        // 复制文件内容
+        Files.copy(multipartFile.getInputStream(), path, StandardCopyOption.REPLACE_EXISTING);
+        return convFile;
+    }
+
+}

+ 2 - 1
src/main/resources/application.properties

@@ -7,7 +7,8 @@ spring.datasource.username=postgres
 spring.datasource.password=WE176852439@lmx
 spring.jpa.hibernate.ddl-auto=update
 spring.jpa.show-sql=true
-
+spring.servlet.multipart.max-file-size=300MB
+spring.servlet.multipart.max-request-size=300MB
 
 zip_file_path: ${ZIP_FILE_PATH:C:/Users/Liumouren/Desktop/}
 zip_file_name: ${ZIP_FILE_NAME:outFile}