簡體   English   中英

解析CSV文件以填充數據庫

[英]Parsing a csv file to populate database

鑒於我有一個這樣的CSV文件

str_name,int_points,int_bonus
joe,2,5
Moe,10,15
Carlos,25,60

我可以使用具有x列數和y行數的csv文件,因此我正在嘗試開發一種通用方法來對其進行解析並將數據填充到dynamodb表中。

為了填充dynamodb表,我會做這樣的事情

String line = "";
    String cvsSplitBy = ",";

    try (BufferedReader br = new BufferedReader(
                                new InputStreamReader(objectData, "UTF-8"));

        while ((line = br.readLine()) != null) {

            // use comma as separator
            String[] elements = line.split(cvsSplitBy);

            try {
                table.putItem(new Item()
                    .withPrimaryKey("name", elements[0])
                    .withInt("points", elements[1])
                    .withInt("bonus", elements[2])
                    .....);

                System.out.println("PutItem succeeded: " + elements[0]);

            } catch (Exception e) {
                System.err.println("Unable to add user: " + elements);
                System.err.println(e.getMessage());
                break;
            }

        }

    } catch (IOException e) {
        e.printStackTrace();
    }

但是我並不總是知道我是否正在插入一個int或字符串,它取決於csv文件,所以我有點迷失於如何創建一個通用函數,該函數將讀取我的csv文件的第一行並利用前綴指示特定的列是int還是字符串。

只需存儲標簽(第一行),然后在遍歷行值時,根據標簽確定要調用的方法。 如果您不反對引入某些外部依賴項,建議您使用一些外部csv讀取器,例如SuperCsv。使用此庫,您可以例如將每一行讀取為Map(label-> val),然后遍歷條目並基於標簽前綴更新您的數據庫使用正確的方法。 或者只是讀取標題,然后以相同的方式讀取每一行作為列表。

范例:

這當然是非常粗糙的,我可能會以某種方式對其進行重構(例如,為每列提供一個處理器列表而不是難看的開關),但是它向您展示了這個想法

        List<String> labels = new ArrayList<>();//store first row here
        List<String> elements = new ArrayList<>();//currently processed line here
        Item item = new Item();
        for (int i = 0; i < elements.size(); i++) {
            String label = labels.get(i);
            switch (getTypePrefix(label)){
                case "int":
                    item = item.withInt(getName(label),elements.get(i));
                    break;
                case "str":
                    item = item.withString(getName(label),elements.get(i));
                    break;
                default:
                    //sth
                    break;
            }
        }
        table.putItem(item);

好的,我不能將其發布為評論,所以我寫了一個簡單的示例。 請注意,我對您所使用的Amazon API並不熟悉,但是您應該了解如何使用它(我基本上已經重寫了您的代碼)

        String line = "";
        String cvsSplitBy = ",";

        try (BufferedReader br = new BufferedReader(
                            new InputStreamReader(objectData, "UTF-8"));

     String[]  colNames = br.readLine().split(cvsSplitBy);      //first line just to get the column names
     while ((line = br.readLine()) != null) {
        String currColumnName = colNames.get(i);
        // use comma as separator
        String[] elements = line.split(cvsSplitBy);
        boolean isInt ;
        for (int i = 0; i < elements.length;i++){

        try {
            try{
            int iVal = new Integer(elements[i]);
            isInt = true;
            }catch(NumberFormatException e){
            //process exception
            isInt = false;
            }
            if(isInt){
            table.putItem.(new Item().withInt(currColumnName,iVal));
            }else{
            table.putItem.(new Item().withString(currColumnName),elements[i])); //don't even know whether there is a withString method
            }

            System.out.println("PutItem succeeded: " + elements[i]);

        } catch (Exception e) {
            System.err.println("Unable to add user: " + elements);
            System.err.println(e.getMessage());
            break;
        }
        }

    }

} catch (IOException e) {
    e.printStackTrace();
}

本示例假定您的第一行包含存儲在數據庫中的列名。 您不必在任何地方編寫它們,無論它們是int還是String都可以,因為程序中有檢查(當然,這不是執行此操作的最有效方法,您可以編寫更好的東西,也許是Molok的建議)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM