Каков наилучший / быстрый способ загрузки этих файлов .csv? - PullRequest
1 голос
/ 22 марта 2019

Я пытался загрузить 6 .csv файлов.Я использовал библиотеку CSVReader и библиотеку BufferedReader.Я заметил, что при использовании библиотеки BufferedReader файлы загружаются быстрее.Тем не менее, это вызвало у меня исключение OutOfMemory, поэтому мне пришлось установить максимальное использование памяти в Eclipse 1024 МБ.С другой стороны, когда я использую библиотеку CSVReader, я не вижу этой проблемы.Мне интересно, есть ли что-то не так в моем коде, и что может быть лучшим способом загрузки файлов, считая это оптимальным с точки зрения скорости и памяти.Вот мой код (я использую BufferedReader здесь):

public void loadMovingViolations(int semestre)
{
    try
    {
        String path = ".\\data\\Moving_Violations_Issued_in_";
        String mth1Path = "";
        String mth2Path = "";
        String mth3Path = "";
        String mth4Path = "";
        String mth5Path = "";
        String mth6Path = "";

        if (semestre == 1)
        {
            mth1Path = path + "January_2018.csv";
            mth2Path = path + "February_2018.csv";
            mth3Path = path + "March_2018.csv";
            mth4Path = path + "April_2018.csv";
            mth5Path = path + "May_2018.csv";
            mth6Path = path + "June_2018.csv";
        }

        else if (semestre == 2)
        {
            mth1Path = path + "July_2018.csv";
            mth2Path = path + "August_2018.csv";
            mth3Path = path + "September_2018.csv";
            mth4Path = path + "October_2018.csv";
            mth5Path = path + "November_2018.csv";
            mth6Path = path + "December_2018.csv";
        }

        String[] mths = {mth1Path, mth2Path, mth3Path, mth4Path, mth5Path, mth6Path};
        String cPath = "";

        int numInfracs = 0;
        int[] infracs = new int[6];
        double xMin = Double.MAX_VALUE, yMin = Double.MAX_VALUE, xMax = 0, yMax = 0;
        BufferedReader br = null;

        int i = 0;
        while (i < mths.length)
        {
            int tempInfrac = 0;
            cPath = mths[i];
            br = new BufferedReader(new FileReader(cPath));
            String row = br.readLine();

            while ( (row = br.readLine()) != null)
            {   
                String[] columns = row.split(",");

                String in1 = columns[0];
                Integer objId = Integer.parseInt(in1);

                String location = columns[2];

                String in2 = columns[3];
                int adressId = 0;
                if ( !(in2.compareTo("") == 0) )
                    adressId = Integer.parseInt(in2);

                String in3 = columns[4];
                double streetId = 0;
                if ( !(in3.compareTo("") == 0) )
                    streetId = Double.parseDouble(in3);

                String in4 = columns[5];
                Double xCord = Double.parseDouble(in4);

                String in5 = columns[6];
                Double yCord = Double.parseDouble(in5);

                String ticketType = columns[7];

                String in6 = columns[8];
                Integer fineAmt = Integer.parseInt(in6);

                String in7 = columns[9];
                double totalPaid = Double.parseDouble(in7);

                String in8 = columns[10];
                Integer penalty1 =  Integer.parseInt(in8);

                String accident = columns[12];

                String date = columns[13];

                String vioCode = columns[14];

                String vioDesc = columns[15];

                VOMovingViolations vomv = new VOMovingViolations(objId, location, adressId, streetId, xCord, yCord, ticketType, fineAmt, totalPaid, penalty1, accident, date, vioCode, vioDesc);
                movingViolationsQueue.enqueue(vomv);
                tempInfrac++;

                if (xCord > xMax)
                    xMax = xCord;

                if (yCord > yMax)
                    yMax = yCord;

                if (xCord < xMin)
                    xMin = xCord;

                if (yCord < yMin)
                    yMin = yCord;
            }

            numInfracs += tempInfrac;
            infracs[i] = tempInfrac;
            i++;
            br.close();
        }

        System.out.println();
        int j = 0;
        for (int current: infracs)
        {
            String[] sa = mths[j].substring(35).split("_");
            String mth = sa[0];
            System.out.println("En el mes " + mth + " se encontraron " + 
                                current + " infracciones");
            j++;
        }
        System.out.println();
        System.out.println("Se encontraron " + numInfracs + " infracciones en el semestre.");
        System.out.println();
        System.out.println("Minimax: " + "("+xMin+", "+yMin+"), " + "("+xMax+", "+yMax+")");
        System.out.println();
    }

    catch (Exception e)
    {
        e.printStackTrace();
        System.out.println();
        System.out.println("No se pudieron cargar los datos");
        System.out.println();
    }
}

Ответы [ 2 ]

1 голос
/ 22 марта 2019

Относительно «лучшего» пути, как обычно, все зависит.

Вы заново изобретаете колесо.И на удивление сложно написать полнофункциональный парсер csv, который работает с произвольными входными данными.Ваш синтаксический анализатор делает простое разделение на «,», это означает, что он потерпит неудачу, как только один из ваших столбцов содержит строку с запятой внутри!Вы также можете столкнуться с проблемами при изменении символа разделения.

Ваш код работает быстрее, потому что в нем пропущено множество вещей, которые может сделать парсер csv.Поэтому ваш код работает с вашей таблицей, но если кто-то другой даст вам действительный файл CSV, ваш парсер будет выдавать вам исключения.Настоящий csv-парсер будет принимать любой правильно сформированный ввод!

Таким образом: если единственной целью вашего кода является чтение файлов с данной структурой, конечно, вы можете использовать ваше более быстрое решение.Но если вы ожидаете, что формат входных данных со временем изменится, то каждое обновление заставит вас изменить свой код.И что еще хуже, такие обновления могут усложнить ваш код с течением времени.Поэтому вы должны тщательно сбалансировать эффективность разработки с производительностью во время выполнения.

0 голосов
/ 22 марта 2019

Спасибо за ваши ответы. Я попытался использовать другую библиотеку, и теперь загрузка файлов занимает всего около 1,2 секунды (я загружаю около 600 тыс. Объектов). Но я все еще получаю OutOfMemory: исключение кучи Java, когда я не помещаю Xms512m и Xml1024m в команды Eclipse. Есть ли способ заставить мой метод загрузки использовать меньше памяти?

public void loadMovingViolations(int semestre)
{
    CsvParserSettings settings = new CsvParserSettings();
    settings.getFormat().setLineSeparator("\n");
    CsvParser parser = new CsvParser(settings);

    String path = ".\\data\\Moving_Violations_Issued_in_";
    String mth1Path = "";
    String mth2Path = "";
    String mth3Path = "";
    String mth4Path = "";
    String mth5Path = "";
    String mth6Path = "";

    if (semestre == 1)
    {
        mth1Path = path + "January_2018.csv";
        mth2Path = path + "February_2018.csv";
        mth3Path = path + "March_2018.csv";
        mth4Path = path + "April_2018.csv";
        mth5Path = path + "May_2018.csv";
        mth6Path = path + "June_2018.csv";
    }

    else if (semestre == 2)
    {
        mth1Path = path + "July_2018.csv";
        mth2Path = path + "August_2018.csv";
        mth3Path = path + "September_2018.csv";
        mth4Path = path + "October_2018.csv";
        mth5Path = path + "November_2018.csv";
        mth6Path = path + "December_2018.csv";
    }

    String[] mths = {mth1Path, mth2Path, mth3Path, mth4Path, mth5Path, mth6Path};
    String cPath = "";

    int numInfracs = 0;
    int[] infracs = new int[6];
    double xMin = Double.MAX_VALUE, yMin = Double.MAX_VALUE, xMax = 0, yMax = 0;

    try
    {
        int i = 0;
        while (i < mths.length)
        {
            int tempInfrac = 0;
            cPath = mths[i];
            parser.beginParsing(new FileReader(cPath));
            parser.parseNext();
            String[] row = null;
            while((row = parser.parseNext()) != null)
            {
                String in1 = row[0].toString();
                Integer objId = Integer.parseInt(in1);

                String location = row[2].toString();

                int addressId = 0;
                if (row[3] != null)
                {
                    String in2 = row[3].toString();
                    addressId = Integer.parseInt(in2);
                }

                double streetId = 0;
                if (row[4] != null)
                {
                    String in3 = row[4].toString();
                    streetId = Double.parseDouble(in3);
                }

                String in4 = row[5].toString();
                Double xCord = Double.parseDouble(in4);

                String in5 = row[6].toString();
                Double yCord = Double.parseDouble(in5);

                String ticketType = row[7].toString();

                String in6 = row[8].toString();
                Integer fineAmt = Integer.parseInt(in6);

                String in7 = row[9].toString();
                double totalPaid = Double.parseDouble(in7);

                String in8 = row[10].toString();
                Integer penalty1 =  Integer.parseInt(in8);

                String accident = row[12].toString();

                String date = "";
                if (row[13] != null)
                    date = row[13].toString();

                String vioCode = row[14].toString();

                String vioDesc = "";
                if (row[15] != null)
                    vioDesc = row[15].toString();

                VOMovingViolations vomv = new VOMovingViolations(objId, location, addressId, streetId, xCord, yCord, ticketType, fineAmt, totalPaid, penalty1, accident, date, vioCode, vioDesc);
                queue.enqueue(vomv);
                tempInfrac++;

                if (xCord > xMax)
                    xMax = xCord;

                if (yCord > yMax)
                    yMax = yCord;

                if (xCord < xMin)
                    xMin = xCord;

                if (yCord < yMin)
                    yMin = yCord;
            }

            numInfracs += tempInfrac;
            infracs[i] = tempInfrac;
            parser.stopParsing();
            i++;
        }

        System.out.println();
        int j = 0;
        for (int current: infracs)
        {
            String[] sa = mths[j].substring(35).split("_");
            String mth = sa[0];
            System.out.println("En el mes " + mth + " se encontraron " + 
                                current + " infracciones");
            j++;
        }
        System.out.println();
        System.out.println("Se encontraron " + numInfracs + " infracciones en el semestre.");
        System.out.println();
        System.out.println("Minimax: " + "("+xMin+", "+yMin+"), " + "("+xMax+", "+yMax+")");
        System.out.println();
    }

    catch (FileNotFoundException e)
    {
        e.printStackTrace();
        System.out.println();
        System.out.println("No se encontró el archivo");
        System.out.println();
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...