【问题标题】:merge csv files into one document with no repeats in row Java将 csv 文件合并到一个文档中,Java 行中没有重复
【发布时间】:2021-12-30 10:44:11
【问题描述】:

我必须合并两个 csv 文件。 我已经实现了一些代码并且文件合并但是我从第二个文档中得到重复的行写入新行。 像这样 : D,M,20211217,test17045,ehdef,ase_17045_26332@ukuat.com,38008621179,2021092700210571,16880,17045,UID1704510000037,1704537,222,0,200000101,0 第一个文件, D,M,20211217,2021092700210471,UID1704510000027,16880,17045 //第二个文件。

我希望通过 UniqueID 字段将两行合并在一起。 这是 CSV 解析器: 公共类 CsvParser {

// 代码

    public static List<CsvVo> getRecodrsFromACsv(File file, List<String> keys) throws IOException {
        BufferedReader br = new BufferedReader(new FileReader(file));
        List<CsvVo> records = new ArrayList<>();
        boolean isHeader = true;

        String line = null;
        while ((line = br.readLine()) != null) {
            if (isHeader) {// first line is header
                isHeader = false;
                continue;
            }
            CsvVo record = new CsvVo(file.getName());
            String[] lineSplit = line.split(", ");
            for (int i = 0; i < lineSplit.length; i++) {
                record.put(keys.get(i), lineSplit[i]);
            }
            records.add(record);
        }

        br.close();

        return records;
    }

    public static List<String> getHeadersFromACsv(File file) throws IOException {
//        if (file.exists()) {
            BufferedReader br = new BufferedReader(new FileReader(file));
            List<String> headers = null;

            String line = null;
            while ((line = br.readLine()) != null) {
                String[] lineSplit = line.split(", ");
                headers = new ArrayList<>(Arrays.asList(lineSplit));
                log.info("HEADERS : " + headers);
                break;
            }

            br.close();

            return headers;

//    }
//        return null;
    }
    public static void writeToCsv(final File file, final Set<String> headers, final List<CsvVo> records)
            throws IOException {
        FileWriter csvWriter = new FileWriter(file);

        // write headers
        String sep = "";
        String[] headersArr = headers.toArray(new String[headers.size()]);
        for (String header : headersArr) {
            csvWriter.append(sep);
            csvWriter.append(header);
            sep = "|";
        }

        csvWriter.append("\n");

        // write records at each line
        for (CsvVo record : records) {
            sep = "";
            for (String s : headersArr) {
                csvWriter.append(sep);
                csvWriter.append(record.get(s));
                sep = "|";
            }
            csvWriter.append("\n");
        }

        csvWriter.flush();
        csvWriter.close();
    }

这是合并模型 //代码

public class CsvVo {

    private Map<String, String> keyVal;

    public CsvVo(String id) {
        keyVal = new LinkedHashMap<>();// you may also use HashMap if you don't need to keep order
    }

    public Map<String, String> getKeyVal() {
        return keyVal;
    }

    public void setKeyVal(Map<String, String> keyVal) {
        this.keyVal = keyVal;
    }

    public void put(String key, String val) {
        keyVal.put(key, val);
    }

    public String get(String key) {
        return keyVal.get(key);
    }

这是实现: //代码

File aseFile = new File("merge/mergeFile.txt");
        File newFile = new File("dpcFileReturn.txt");
        log.info("File To Be Processed : " + newFile.getName());

        List<String> csv1Headers = CsvParser.getHeadersFromACsv(aseFile);
        csv1Headers.forEach(h -> System.out.print(h + " "));
        // System.out.println();
        List<String> csv2Headers = CsvParser.getHeadersFromACsv(newFile);
        csv2Headers.forEach(h -> System.out.print(h + " "));
        // System.out.println();

        List<String> allCsvHeaders = new ArrayList<>();
        allCsvHeaders.addAll(csv1Headers);
        allCsvHeaders.addAll(csv2Headers);
        allCsvHeaders.forEach(h -> System.out.print(h + " "));
        // System.out.println();

        Set<String> uniqueHeaders = new HashSet<>(allCsvHeaders);
        uniqueHeaders.forEach(h -> System.out.print(h + " "));
        // System.out.println();

        List<CsvVo> csv1Records = CsvParser.getRecodrsFromACsv(aseFile, csv1Headers);
        List<CsvVo> csv2Records = CsvParser.getRecodrsFromACsv(newFile, csv2Headers);

        List<CsvVo> allCsvRecords = new ArrayList<>();
        allCsvRecords.addAll(csv1Records);
        allCsvRecords.addAll(csv2Records);

        File mergedFile = new File("mergedFile.txt");
        CsvParser.writeToCsv(new File("mergedFile.txt"), uniqueHeaders, allCsvRecords);

        log.info("Merged File : " + mergedFile);

The first file
recordType,activityType,activityDate,foreName,surName,emailAddress,mobilePhone,dpid,clientID,programmeID,uniqueID,bankAccount,sortCode,isJointAccount,dateOfBirth,addressLine1,postCode,clientReference,suspension,
D|M|20211217|test17045|afdib|ase_17045_29894@ukuat.com|30934992219|2021092700210261|16880|17045|UID1704510000006|1704506|003|0|20000101|London|510000||0|
D|M|20211217|test17045|ibabi|ase_17045_42069@ukuat.com|07676909173|2021092700210271|16880|17045|UID1704510000007|1704507|278|0|20000101|London|510000||0|

secondFile
H,activityType,activityDate,dpid,uniqueID,clientID,programmeID, D,M,20211217,2021092700210261,UID1704510000006,16880,17045, D,M,20211217,2021092700210271,UID1704510000007,16880,17045,

我正在寻找一个合并文件,该文件包含用户名、姓氏、电子邮件和/或唯一 ID,并验证数据并用新(缺失)数据(如果有)覆盖该行。

我什么也找不到,我什至尝试使用嵌套循环来检查文件 1 的行子字符串与文件 2 的对比。但似乎无法正常工作。

任何帮助将不胜感激。

【问题讨论】:

    标签: java csv merge


    【解决方案1】:

    合并是将第一个CSV文件中的数据替换为第二个文件中对应的新数据,如果有的话,并将结果保存为新文件。 Java 没有专门的类库来执行面向集合的计算,所以这个过程会很迂回。

    您可以使用 Java 的开源包 SPL 来执行此操作。几行就够了:

      A
    1 =file("mergeFile.txt").import@ct()
    2 =file("dpcFileReturn.txt").import@ct()
    3 >A1.run(~.modify@f(ifn(A2.select@1(uniqueID==A1.uniqueID &&   activityDate>A1.activityDate),~)))
    4 =file("mergedFile.txt").export@ct(A1)

    SPL 提供 JDBC 驱动程序以供 Java 程序调用。只需将上述SPL脚本存储为mergeFile.splx,在Java中以调用存储过程的方式调用即可:

    …
    
    Class.forName("com.esproc.jdbc.InternalDriver");
    
    con = DriverManager.getConnection("jdbc:esproc:local://");
    
    st = con.prepareCall("call mergeFile ()");
    
    st.execute();
    
    …
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-11-01
      • 2020-02-04
      • 2017-11-03
      • 2021-11-26
      • 1970-01-01
      • 2011-08-29
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多