Количество строк в файле на Java

Я использую огромные файлы данных, иногда мне нужно знать только количество строк в этих файлах, обычно я открываю их и читаю построчно, пока не дойду до конца файла.

Мне было интересно, есть ли способ сделать это поумнее


person Mark    schedule 17.01.2009    source источник


Ответы (19)


Это самая быстрая версия, которую я нашел до сих пор, примерно в 6 раз быстрее, чем readLines. В файле журнала размером 150 МБ это занимает 0,35 секунды по сравнению с 2,40 секунды при использовании readLines (). Ради удовольствия, команда wc -l в linux занимает 0,15 секунды.

public static int countLinesOld(String filename) throws IOException {
    InputStream is = new BufferedInputStream(new FileInputStream(filename));
    try {
        byte[] c = new byte[1024];
        int count = 0;
        int readChars = 0;
        boolean empty = true;
        while ((readChars = is.read(c)) != -1) {
            empty = false;
            for (int i = 0; i < readChars; ++i) {
                if (c[i] == '\n') {
                    ++count;
                }
            }
        }
        return (count == 0 && !empty) ? 1 : count;
    } finally {
        is.close();
    }
}

РЕДАКТИРОВАТЬ, 9 1/2 лет спустя: у меня практически нет опыта работы с java, но в любом случае я попытался сравнить этот код с решением LineNumberReader, приведенным ниже, поскольку меня беспокоило, что этого никто не делал. Кажется, что особенно для больших файлов мое решение работает быстрее. Хотя, кажется, потребуется несколько прогонов, пока оптимизатор не выполнит достойную работу. Я немного поигрался с кодом и создал новую, неизменно самую быструю версию:

public static int countLinesNew(String filename) throws IOException {
    InputStream is = new BufferedInputStream(new FileInputStream(filename));
    try {
        byte[] c = new byte[1024];

        int readChars = is.read(c);
        if (readChars == -1) {
            // bail out if nothing to read
            return 0;
        }

        // make it easy for the optimizer to tune this loop
        int count = 0;
        while (readChars == 1024) {
            for (int i=0; i<1024;) {
                if (c[i++] == '\n') {
                    ++count;
                }
            }
            readChars = is.read(c);
        }

        // count remaining characters
        while (readChars != -1) {
            System.out.println(readChars);
            for (int i=0; i<readChars; ++i) {
                if (c[i] == '\n') {
                    ++count;
                }
            }
            readChars = is.read(c);
        }

        return count == 0 ? 1 : count;
    } finally {
        is.close();
    }
}

Результаты теста для текстового файла объемом 1,3 ГБ, ось Y в секундах. Я выполнил 100 прогонов с одним и тем же файлом и измерил каждый прогон с System.nanoTime(). Вы можете видеть, что у countLinesOld есть несколько выбросов, а у countLinesNew их нет, и хотя он только немного быстрее, разница статистически значима. LineNumberReader явно медленнее.

«Контрольный

person martinus    schedule 17.01.2009
comment
Вы были правы, Дэвид, я думал, что JVM подойдет для этого ... Я обновил код, этот работает быстрее. - person martinus; 17.01.2009
comment
BufferedInputStream должен выполнять буферизацию за вас, поэтому я не понимаю, как использование промежуточного массива byte [] сделает это быстрее. В любом случае вы вряд ли добьетесь большего успеха, чем многократное использование readLine () (поскольку это будет оптимизировано для API). - person wds; 17.01.2009
comment
Ive протестировал его с буферизованным входным потоком и без него, и при его использовании он работает быстрее. - person martinus; 17.01.2009
comment
Вы собираетесь закрыть этот InputStream, когда закончите с ним, не так ли? - person bendin; 24.05.2009
comment
Если бы буферизация помогла, это было бы, потому что BufferedInputStream по умолчанию буферизует 8 КБ. Увеличьте свой byte [] до этого или большего размера, и вы можете отбросить BufferedInputStream. например попробуйте 1024 * 1024 байта. - person Peter Lawrey; 24.05.2009
comment
Работает хорошо, пока я не использую его в некоторых файлах формата MAC или некоторых файлах, в которых последняя строка не имеет символа '\ n'. В таких ситуациях номер будет неправильным. Хотя это быстро, но я думаю, что буду придерживаться универсального метода readLine (). - person newguy; 14.03.2011
comment
Две вещи: (1) Определение терминатора строки в исходном коде Java - это возврат каретки, перевод строки или возврат каретки, за которым следует перевод строки. Ваше решение не будет работать для CR, используемого в качестве ограничителя строки. Конечно, единственная ОС, которая, как мне кажется, использует CR в качестве ограничителя строки по умолчанию, - это Mac OS до Mac OS X. (2) Ваше решение предполагает кодировку символов, такую ​​как US-ASCII или UTF-8. Счетчик строк может быть неточным для таких кодировок, как UTF-16. - person Nathan Ryan; 21.09.2012
comment
@Nathan_Ryan: Я только что получил логи от java-приложения, которые выводят некоторые ответы службы TCP мэйнфрейма, и внутри было несколько CR. Программа, использовавшая приведенный выше фрагмент, корректно завершилась неудачно. - person serg.nechaev; 28.11.2013
comment
Хороший. Я бы сделал этот метод статическим и переименовал бы его в countLines. Ваше здоровье - person doc; 28.03.2014
comment
Как бы то ни было, у меня уже был byte [] и я использовал следующее: `private int countLines (byte [] file) выбрасывает IOException {InputStream is = new ByteArrayInputStream (file); - person Peter; 20.02.2015
comment
Этот метод показывает на одну строчку меньше ... Попробуйте посмотреть мой ответ ниже. - person Ernestas Gruodis; 21.02.2015
comment
Он не будет работать с файлами, которые используют что-то еще, кроме того, что включает \n в качестве признака конца строки. Счетчик уменьшился на один (на один меньше) для noeol файлов. На самом деле нужно подсчитывать не количество \n, а количество появлений последовательностей символов, разделенных символом конца строки. - person Christian Hujer; 05.03.2015
comment
Попробуйте использовать ресурсы - лучший способ сделать это. try (InputStream is = new BufferedInputStream (new FileInputStream (имя файла))) {// остальная часть кода, как указано выше, без блока finally} - person user4321; 29.08.2016
comment
Потрясающий код ... для текстового файла 400 МБ, это заняло всего секунду. Большое спасибо @martinus - person user3181500; 02.11.2017

Я реализовал другое решение проблемы, счел более эффективным подсчет строк:

try
(
   FileReader       input = new FileReader("input.txt");
   LineNumberReader count = new LineNumberReader(input);
)
{
   while (count.skip(Long.MAX_VALUE) > 0)
   {
      // Loop just in case the file is > Long.MAX_VALUE or skip() decides to not read the entire file
   }

   result = count.getLineNumber() + 1;                                    // +1 because line index starts at 0
}
person er.vikas    schedule 17.03.2011
comment
Поле LineNumberReader lineNumber является целым числом ... Не будет ли оно просто переноситься для файлов длиннее Integer.MAX_VALUE? Зачем пропускать здесь долгое время? - person epb; 03.04.2015
comment
Добавление одного к счету на самом деле неверно. wc -l подсчитывает количество символов новой строки в файле. Это работает, поскольку каждая строка заканчивается новой строкой, включая последнюю строку в файле. Каждая строка имеет символ новой строки, включая пустые строки, следовательно, количество символов новой строки == количество строк в файле. Теперь переменная lineNumber в FileNumberReader также представляет количество увиденных символов новой строки. Он начинается с нуля до того, как будет найден какой-либо символ новой строки, и увеличивается с каждым видимым символом новой строки. Поэтому, пожалуйста, не добавляйте единицу к номеру строки. - person Alexander Torstling; 16.02.2016
comment
@PB_MLT: Хотя вы правы в том, что файл с одной строкой без новой строки будет отображаться как 0 строк, wc -l также сообщает об этом типе файла. Также см. http://stackoverflow.com/questions/729692/why-should-text-files-end-with-a-newline - person Alexander Torstling; 16.02.2016
comment
@PB_MLT: у вас возникает противоположная проблема, если файл состоит исключительно из новой строки. Ваш предлагаемый алгоритм вернет 0, а wc -l вернет 1. Я пришел к выводу, что все методы имеют недостатки, и реализовал один в зависимости от того, как я хотел бы, чтобы он вел себя, см. Другой мой ответ здесь. - person Alexander Torstling; 16.02.2016
comment
Я не проголосовал за этот ответ, потому что, похоже, никто из вас не сравнивал его - person amstegraf; 01.02.2017

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

public int count(String filename) throws IOException {
    InputStream is = new BufferedInputStream(new FileInputStream(filename));
    try {
        byte[] c = new byte[1024];
        int count = 0;
        int readChars = 0;
        boolean endsWithoutNewLine = false;
        while ((readChars = is.read(c)) != -1) {
            for (int i = 0; i < readChars; ++i) {
                if (c[i] == '\n')
                    ++count;
            }
            endsWithoutNewLine = (c[readChars - 1] != '\n');
        }
        if(endsWithoutNewLine) {
            ++count;
        } 
        return count;
    } finally {
        is.close();
    }
}
person DMulligan    schedule 19.01.2013
comment
Хороший улов. Не уверен, почему вы просто не отредактировали принятый ответ и не сделали пометку в комментарии. Большинство людей не станут читать так далеко. - person Ryan; 12.12.2013
comment
@Ryan, мне казалось неправильным редактировать принятый ответ 4-летней давности с 90+ голосами. - person DMulligan; 12.12.2013
comment
@AFinkelstein, я считаю, что это то, что делает этот сайт таким замечательным, что вы можете редактировать ответ, получивший наибольшее количество голосов. - person Sebastian; 27.01.2014
comment
Это решение не обрабатывает возврат каретки (\ r) и возврат каретки, за которыми следует перевод строки (\ r \ n) - person Simon Brandhof - SonarSource; 05.02.2014
comment
@Simon Brandhof, я не понимаю, почему возврат каретки считается другой строкой? A \ n - это перевод строки возврата каретки, поэтому тот, кто пишет \ r \ n, чего-то не понимает ... Кроме того, он ищет char по char, поэтому я почти уверен, что если бы кто-то использовал \ r \ n, он все равно поймайте \ n и посчитайте строку. В любом случае, я думаю, он прекрасно изложил свою точку зрения. Однако существует множество сценариев, в которых этого недостаточно для подсчета количества строк. - person nckbrz; 08.04.2014

С помощью java-8 вы можете использовать потоки:

try (Stream<String> lines = Files.lines(path, Charset.defaultCharset())) {
  long numOfLines = lines.count();
  ...
}
person msayag    schedule 25.07.2013
comment
В коде есть ошибки. Просто, но очень медленно ... Попробуйте посмотреть мой ответ ниже (вверху). - person Ernestas Gruodis; 21.02.2015

Ответ с помощью метода count () выше дал мне неправильный счет строк, если файл не имел новой строки в конце файла - он не смог подсчитать последнюю строку в файле.

Мне больше подходит этот метод:

public int countLines(String filename) throws IOException {
    LineNumberReader reader  = new LineNumberReader(new FileReader(filename));
int cnt = 0;
String lineRead = "";
while ((lineRead = reader.readLine()) != null) {}

cnt = reader.getLineNumber(); 
reader.close();
return cnt;
}
person Dave Bergert    schedule 29.10.2009
comment
В этом случае нет необходимости использовать LineNumberReader, просто используйте BufferedReader, в этом случае вы можете гибко использовать длинный тип данных для cnt. - person Syed Aqeel Ashiq; 30.01.2014
comment
[ИНФОРМАЦИЯ] Ошибка PMD: xx: 19 Правило: EmptyWhileStmt Приоритет: 3 Избегайте пустых операторов while. - person Chhorn Elit; 01.01.2020

Я протестировал вышеуказанные методы для подсчета линий, и вот мои наблюдения для различных методов, проверенных в моей системе.

Размер файла: 1,6 Гб Методы:

  1. С помощью сканера: прибл. 35 с.
  2. Использование BufferedReader: примерно 5 с
  3. При использовании Java 8: примерно 5 с
  4. Использование LineNumberReader: примерно 5 с.

Более того, подход Java8 кажется весьма удобным:

Files.lines(Paths.get(filePath), Charset.defaultCharset()).count()
[Return type : long]
person Anshul    schedule 19.11.2018

Я знаю, что это старый вопрос, но принятое решение не совсем соответствовало тому, что мне нужно было сделать. Итак, я усовершенствовал его, чтобы принимать различные символы конца строки (а не только перевод строки) и использовать указанную кодировку символов (вместо ISO-8859- n). Все в одном методе (при необходимости рефакторинг):

public static long getLinesCount(String fileName, String encodingName) throws IOException {
    long linesCount = 0;
    File file = new File(fileName);
    FileInputStream fileIn = new FileInputStream(file);
    try {
        Charset encoding = Charset.forName(encodingName);
        Reader fileReader = new InputStreamReader(fileIn, encoding);
        int bufferSize = 4096;
        Reader reader = new BufferedReader(fileReader, bufferSize);
        char[] buffer = new char[bufferSize];
        int prevChar = -1;
        int readCount = reader.read(buffer);
        while (readCount != -1) {
            for (int i = 0; i < readCount; i++) {
                int nextChar = buffer[i];
                switch (nextChar) {
                    case '\r': {
                        // The current line is terminated by a carriage return or by a carriage return immediately followed by a line feed.
                        linesCount++;
                        break;
                    }
                    case '\n': {
                        if (prevChar == '\r') {
                            // The current line is terminated by a carriage return immediately followed by a line feed.
                            // The line has already been counted.
                        } else {
                            // The current line is terminated by a line feed.
                            linesCount++;
                        }
                        break;
                    }
                }
                prevChar = nextChar;
            }
            readCount = reader.read(buffer);
        }
        if (prevCh != -1) {
            switch (prevCh) {
                case '\r':
                case '\n': {
                    // The last line is terminated by a line terminator.
                    // The last line has already been counted.
                    break;
                }
                default: {
                    // The last line is terminated by end-of-file.
                    linesCount++;
                }
            }
        }
    } finally {
        fileIn.close();
    }
    return linesCount;
}

Это решение сравнимо по скорости с принятым решением, примерно на 4% медленнее в моих тестах (хотя тесты времени на Java, как известно, ненадежны).

person Nathan Ryan    schedule 21.09.2012

/**
 * Count file rows.
 *
 * @param file file
 * @return file row count
 * @throws IOException
 */
public static long getLineCount(File file) throws IOException {

    try (Stream<String> lines = Files.lines(file.toPath())) {
        return lines.count();
    }
}

Проверено на JDK8_u31. Но на самом деле производительность ниже по сравнению с этим методом:

/**
 * Count file rows.
 *
 * @param file file
 * @return file row count
 * @throws IOException
 */
public static long getLineCount(File file) throws IOException {

    try (BufferedInputStream is = new BufferedInputStream(new FileInputStream(file), 1024)) {

        byte[] c = new byte[1024];
        boolean empty = true,
                lastEmpty = false;
        long count = 0;
        int read;
        while ((read = is.read(c)) != -1) {
            for (int i = 0; i < read; i++) {
                if (c[i] == '\n') {
                    count++;
                    lastEmpty = true;
                } else if (lastEmpty) {
                    lastEmpty = false;
                }
            }
            empty = false;
        }

        if (!empty) {
            if (count == 0) {
                count = 1;
            } else if (!lastEmpty) {
                count++;
            }
        }

        return count;
    }
}

Проверено и очень быстро.

person Ernestas Gruodis    schedule 20.02.2015
comment
Это не так. Поэкспериментировал с вашим кодом, и этот метод всегда медленнее. Stream<String> - Time consumed: 122796351 Stream<String> - Num lines: 109808 Method - Time consumed: 12838000 Method - Num lines: 1 И количество строк тоже неправильное - person aw-think; 27.02.2015
comment
Я тестировал на 32-битной машине. Может на 64-битном были бы другие результаты .. А разница была раз в 10 и больше, насколько я помню. Не могли бы вы разместить где-нибудь текст для подсчета строки? Вы можете использовать Notepad2, чтобы видеть разрывы строк для удобства. - person Ernestas Gruodis; 27.02.2015
comment
В этом может быть разница. - person aw-think; 27.02.2015
comment
Если вы заботитесь о производительности, вам в любом случае не следует использовать BufferedInputStream, когда вы собираетесь читать в свой собственный буфер. Кроме того, даже если ваш метод может иметь небольшое преимущество в производительности, он теряет гибкость, поскольку он больше не поддерживает только \r терминаторы строки (старый MacOS) и не поддерживает все кодировки. - person Holger; 14.11.2016

Простой способ использования сканера

static void lineCounter (String path) throws IOException {

        int lineCount = 0, commentsCount = 0;

        Scanner input = new Scanner(new File(path));
        while (input.hasNextLine()) {
            String data = input.nextLine();

            if (data.startsWith("//")) commentsCount++;

            lineCount++;
        }

        System.out.println("Line Count: " + lineCount + "\t Comments Count: " + commentsCount);
    }
person Terry Bu    schedule 14.09.2014

Я пришел к выводу, что wc -l: s метод подсчета новых строк хорош, но возвращает неинтуитивные результаты для файлов, где последняя строка не заканчивается новой строкой.

И решение @er.vikas на основе LineNumberReader, но добавление единицы к счетчику строк возвращало неинтуитивно понятные результаты для файлов, где последняя строка заканчивается новой строкой.

Поэтому я сделал алгоритм, который обрабатывает следующее:

@Test
public void empty() throws IOException {
    assertEquals(0, count(""));
}

@Test
public void singleNewline() throws IOException {
    assertEquals(1, count("\n"));
}

@Test
public void dataWithoutNewline() throws IOException {
    assertEquals(1, count("one"));
}

@Test
public void oneCompleteLine() throws IOException {
    assertEquals(1, count("one\n"));
}

@Test
public void twoCompleteLines() throws IOException {
    assertEquals(2, count("one\ntwo\n"));
}

@Test
public void twoLinesWithoutNewlineAtEnd() throws IOException {
    assertEquals(2, count("one\ntwo"));
}

@Test
public void aFewLines() throws IOException {
    assertEquals(5, count("one\ntwo\nthree\nfour\nfive\n"));
}

А это выглядит так:

static long countLines(InputStream is) throws IOException {
    try(LineNumberReader lnr = new LineNumberReader(new InputStreamReader(is))) {
        char[] buf = new char[8192];
        int n, previousN = -1;
        //Read will return at least one byte, no need to buffer more
        while((n = lnr.read(buf)) != -1) {
            previousN = n;
        }
        int ln = lnr.getLineNumber();
        if (previousN == -1) {
            //No data read at all, i.e file was empty
            return 0;
        } else {
            char lastChar = buf[previousN - 1];
            if (lastChar == '\n' || lastChar == '\r') {
                //Ending with newline, deduct one
                return ln;
            }
        }
        //normal case, return line number + 1
        return ln + 1;
    }
}

Если вам нужны интуитивные результаты, вы можете использовать это. Если вам просто нужна wc -l совместимость, просто используйте решение @ er.vikas, но не добавляйте его к результату и повторите попытку пропустить:

try(LineNumberReader lnr = new LineNumberReader(new FileReader(new File("File1")))) {
    while(lnr.skip(Long.MAX_VALUE) > 0){};
    return lnr.getLineNumber();
}
person Alexander Torstling    schedule 16.02.2016

Как насчет использования класса Process из кода Java? А затем читаем вывод команды.

Process p = Runtime.getRuntime().exec("wc -l " + yourfilename);
p.waitFor();

BufferedReader b = new BufferedReader(new InputStreamReader(p.getInputStream()));
String line = "";
int lineCount = 0;
while ((line = b.readLine()) != null) {
    System.out.println(line);
    lineCount = Integer.parseInt(line);
}

Хотя нужно попробовать. Выложу результаты.

person Sunil Shevante    schedule 29.03.2013

Это забавное решение действительно хорошо работает!

public static int countLines(File input) throws IOException {
    try (InputStream is = new FileInputStream(input)) {
        int count = 1;
        for (int aChar = 0; aChar != -1;aChar = is.read())
            count += aChar == '\n' ? 1 : 0;
        return count;
    }
}
person Ilya Gazman    schedule 30.08.2016

Кажется, что есть несколько разных подходов, которые вы можете использовать с LineNumberReader.

Я сделал это:

int lines = 0;

FileReader input = new FileReader(fileLocation);
LineNumberReader count = new LineNumberReader(input);

String line = count.readLine();

if(count.ready())
{
    while(line != null) {
        lines = count.getLineNumber();
        line = count.readLine();
    }
    
    lines+=1;
}
    
count.close();

System.out.println(lines);

Более того, вы можете использовать метод Java BufferedReader lines () для возврата потока элементов, а затем использовать метод Stream count () для подсчета всех элементов. Затем просто добавьте единицу к выходным данным, чтобы получить количество строк в текстовом файле.

В качестве примера:

FileReader input = new FileReader(fileLocation);
LineNumberReader count = new LineNumberReader(input);

int lines = (int)count.lines().count() + 1;
    
count.close();

System.out.println(lines);
person Conor    schedule 30.07.2020

В системах на базе Unix используйте команду wc в командной строке.

person Peter Hilton    schedule 17.01.2009
comment
@IainmH, ваше второе предложение просто подсчитывает количество записей в текущем каталоге. Не то, что было задумано? (или по запросу ОП) - person The Archetypal Paul; 17.01.2009
comment
@IainMH: это то, что делает wc в любом случае (чтение файла, считая окончания строки). - person PhiLho; 17.01.2009
comment
@PhiLho Вам нужно использовать ключ -l для подсчета строк. (Не так ли? - это было давно) - person Iain Holder; 17.01.2009
comment
@Paul - ты конечно на 100% прав. Моя единственная защита - это то, что я разместил это перед кофе. Я сейчас сообразителен. : D - person Iain Holder; 17.01.2009

Единственный способ узнать, сколько строк в файле - посчитать их. Конечно, вы можете создать метрику из ваших данных, дающую вам среднюю длину одной строки, а затем получить размер файла и разделить его на avg. длина, но это будет неточно.

person Esko    schedule 17.01.2009
comment
Интересно отрицательное голосование, независимо от того, какой инструмент командной строки вы используете, все они в любом случае ДЕЛАЮТ ОДИНАКОВЫЕ ВЕЩИ, только внутренне. Волшебного способа подсчитать количество линий не существует, их приходится считать вручную. Конечно, это можно сохранить как метаданные, но это совсем другая история ... - person Esko; 17.01.2009

Если у вас нет индексных структур, вы не сможете обойтись без чтения всего файла. Но вы можете оптимизировать его, избегая чтения строки за строкой и используя регулярное выражение для соответствия всем признакам конца строки.

person David Schmitt    schedule 17.01.2009
comment
Похоже на отличную идею. Кто-нибудь пробовал это и для него есть регулярное выражение? - person willcodejavaforfood; 17.01.2009
comment
Я сомневаюсь, что это такая хорошая идея: ему нужно будет прочитать весь файл сразу (Мартинус избегает этого), а регулярные выражения излишни (и медленнее) для такого использования (простой поиск фиксированных символов). - person PhiLho; 17.01.2009
comment
@will: а как насчет / \ n /? @PhiLo: Regex Executors - это высокопроизводительные машины с высокой производительностью. Я не думаю, что ручная реализация может быть быстрее, за исключением оговорки о том, что все в памяти читается. - person David Schmitt; 17.05.2011

Наилучший оптимизированный код для многострочных файлов, не имеющих символа новой строки ('\ n') в EOF.

/**
 * 
 * @param filename
 * @return
 * @throws IOException
 */
public static int countLines(String filename) throws IOException {
    int count = 0;
    boolean empty = true;
    FileInputStream fis = null;
    InputStream is = null;
    try {
        fis = new FileInputStream(filename);
        is = new BufferedInputStream(fis);
        byte[] c = new byte[1024];
        int readChars = 0;
        boolean isLine = false;
        while ((readChars = is.read(c)) != -1) {
            empty = false;
            for (int i = 0; i < readChars; ++i) {
                if ( c[i] == '\n' ) {
                    isLine = false;
                    ++count;
                }else if(!isLine && c[i] != '\n' && c[i] != '\r'){   //Case to handle line count where no New Line character present at EOF
                    isLine = true;
                }
            }
        }
        if(isLine){
            ++count;
        }
    }catch(IOException e){
        e.printStackTrace();
    }finally {
        if(is != null){
            is.close();    
        }
        if(fis != null){
            fis.close();    
        }
    }
    LOG.info("count: "+count);
    return (count == 0 && !empty) ? 1 : count;
}
person Pramod Yadav    schedule 10.10.2017

Сканер с регулярным выражением:

public int getLineCount() {
    Scanner fileScanner = null;
    int lineCount = 0;
    Pattern lineEndPattern = Pattern.compile("(?m)$");  
    try {
        fileScanner = new Scanner(new File(filename)).useDelimiter(lineEndPattern);
        while (fileScanner.hasNext()) {
            fileScanner.next();
            ++lineCount;
        }   
    }catch(FileNotFoundException e) {
        e.printStackTrace();
        return lineCount;
    }
    fileScanner.close();
    return lineCount;
}

Еще не засекли.

person user176692    schedule 26.02.2019

если вы используете это

public int countLines(String filename) throws IOException {
    LineNumberReader reader  = new LineNumberReader(new FileReader(filename));
    int cnt = 0;
    String lineRead = "";
    while ((lineRead = reader.readLine()) != null) {}

    cnt = reader.getLineNumber(); 
    reader.close();
    return cnt;
}

вы не можете работать с большим числом строк, любит 100 тысяч строк, потому что return from reader.getLineNumber - это int. вам нужен длинный тип данных для обработки максимального количества строк ..

person Faisal    schedule 13.12.2010
comment
int может содержать значения до примерно 2 миллиардов. Если вы загружаете файл с более чем 2 миллиардами строк, у вас проблема с переполнением. Тем не менее, если вы загружаете неиндексированный текстовый файл с более чем двумя миллиардами строк, у вас, вероятно, есть другие проблемы. - person Adam Norberg; 03.06.2011