В чем основное различие между next() и nextLine()?
Моя основная цель - прочитать весь текст, используя Scanner, который может быть "связан" с любым источником (например, с файлом).

Какой выбрать и почему?

104
AnnieOK 17 Мар 2014 в 19:34
Это может помочь вам [Использование scanner.nextLine ()] [1]: stackoverflow.com / questions / 5032356 / using-scanner-nextline
 – 
Milaci
17 Мар 2014 в 19:40

16 ответов

Лучший ответ

Я всегда предпочитаю читать ввод с помощью nextLine(), а затем анализировать строку.

Использование next() вернет только то, что находится перед разделителем (по умолчанию используется пробел). nextLine() автоматически перемещает сканер вниз после возврата текущей строки.

Полезным инструментом для анализа данных из nextLine() будет str.split("\\s+").

String data = scanner.nextLine();
String[] pieces = data.split("\\s+");
// Parse the pieces

Для получения дополнительной информации о классе Scanner или String перейдите по следующим ссылкам.

Сканер: http://docs.oracle.com/javase /7/docs/api/java/util/Scanner.html

Строка: http://docs.oracle.com/javase /7/docs/api/java/lang/String.html

96
Aron Hoogeveen 21 Окт 2019 в 11:06
5
Так почему бы просто не использовать BufferedReader для построчного чтения? Я не понимаю, почему Scanner в такой моде.
 – 
David Conrad
17 Мар 2014 в 19:51
7
"В чем разница между методами next () и nextLine () из класса Scanner?"
 – 
Tristan
17 Мар 2014 в 19:56
4
Да, я понимаю, что это то, о чем спрашивал ОП, мне просто интересно, поскольку вы говорите, что «всегда предпочитаете» использовать nextLine.
 – 
David Conrad
17 Мар 2014 в 20:13
Вы можете безопасно выполнить nextLine (), а затем создать новый сканер только для этой строки. Класс Scanner может сканировать строки: new Scanner (new Scanner (System.in) .nextLine ()).
 – 
axell-brendow
9 Ноя 2019 в 15:08

Из javadocs

Next () Возвращает следующий токен, если он соответствует шаблону, построенному из указанной строки. nextLine () Продвигает этот сканер за текущую строку и возвращает пропущенный ввод.

Какой из них вы выберете, зависит от того, что лучше всего соответствует вашим потребностям. Если бы я читал весь файл, я бы пошел на nextLine, пока не получил весь файл.

2
onesixtyfourth 17 Мар 2014 в 19:37

Из документации для Scanner:

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

Из документации для next ():

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

1
Foobar 17 Мар 2014 в 19:40

Методы next () и nextLine () связаны со сканером и используются для получения входных данных String. Их отличия ...

Next () может читать ввод только до пробела. Он не может прочитать два слова, разделенных пробелом. Кроме того, next () помещает курсор в ту же строку после чтения ввода.

NextLine () читает ввод, включая пробел между словами (то есть читает до конца строки \ n). Как только ввод прочитан, nextLine () устанавливает курсор на следующую строку.

import java.util.Scanner;

public class temp
{
    public static void main(String arg[])
    {
        Scanner sc=new Scanner(System.in);
        System.out.println("enter string for c");
        String c=sc.next();
        System.out.println("c is "+c);
        System.out.println("enter string for d");
        String d=sc.next();
        System.out.println("d is "+d);
    }
}

Выход:

Введите строку для c abc def
c - это abc

Введите строку для d

D is def

Если вы используете nextLine () вместо next (), тогда

Выход:

Введите строку для c

ABC DEF
c - это ABC DEF
введите строку для d

GHI
d - GHI

4
Musaddique 8 Апр 2015 в 13:26
  • Вот еще один пример Scanner.next () и nextLine (), как показано ниже: nextLine () не позволяет пользователю вводить, в то время как next () заставляет Scanner ждать и читать ввод.

     Scanner sc = new Scanner(System.in);
    
     do {
        System.out.println("The values on dice are :");
        for(int i = 0; i < n; i++) {
            System.out.println(ran.nextInt(6) + 1);
        }
        System.out.println("Continue : yes or no");
     } while(sc.next().equals("yes"));
    // while(sc.nextLine().equals("yes"));
    
1
annoo9605 31 Дек 2015 в 05:31

Обе функции используются для перехода к следующему токену сканера.

Разница заключается в том, как генерируется токен сканера.

next () генерирует токены сканера с использованием разделителя в виде пробела .

nextLine () генерирует токены сканера с использованием разделителя в виде '\ n' (т.е. Enter нажатия клавиш)

1
Aditya Rewari 8 Мар 2020 в 12:22

next() может читать ввод только до пробела. Он не может прочитать два слова, разделенных пробелом. Кроме того, next() помещает курсор в ту же строку после чтения ввода.

nextLine() читает ввод, включая пробелы между словами (то есть читает до конца строки \n). После считывания ввода nextLine() помещает курсор в следующую строку.

Для чтения всей строки вы можете использовать nextLine().

57
Mooncrater 7 Окт 2017 в 04:58
Вы имеете в виду форматирование, а не формальное письмо?
 – 
Det
12 Авг 2019 в 19:57
1
Next () может читать ввод только до пробела . Он не может прочитать два слова, разделенных пробелом . пробел включает пробел, табуляцию и перевод строки
 – 
Fred Hu
13 Сен 2020 в 18:03

Из JavaDoc:

  • Scanner разбивает свой ввод на токены, используя шаблон разделителя, который по умолчанию соответствует пробелам.
  • next(): находит и возвращает следующий полный токен из этого сканера.
  • nextLine(): продвигает этот сканер за пределы текущей строки и возвращает пропущенный ввод.

Таким образом, в случае "small example<eol>text" next() должен возвращать "small", а nextLine() должен возвращать "small example"

19
Mooncrater 6 Окт 2017 в 21:40
1
Почему next() не включает \n в возвращаемый токен ??
 – 
rimalroshan
13 Янв 2019 в 09:31
2
Это вопрос к разработчикам Java API, или задайте вопрос по SO, и, возможно, кто-нибудь знает почему.
 – 
Oleg Sklyar
13 Янв 2019 в 23:48

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

Все методы будут читать информацию, которая не включает пробелы между позицией курсора и следующими разделителями по умолчанию (пробел, табуляция, \ n - создается нажатием Enter). Курсор останавливается перед разделителями, за исключением nextLine(), который считывает информацию (включая пробелы, созданные разделителями) между позицией курсора и \ n, и курсор останавливается за \ n.


Например, рассмотрим следующую иллюстрацию:

|23_24_25_26_27\n

| -> текущая позиция курсора

_ -> пробел

поток -> Полужирный (информация, полученная вызывающим методом)

Посмотрите, что происходит, когда вы вызываете эти методы:

nextInt()    

Прочтите 23 | _24_25_26_27 \ n

nextDouble()

Прочтите 23_ 24 | _25_26_27 \ n

next()

Прочтите 23_24_ 25 | _26_27 \ n

nextLine()

Прочитайте 23_24_25 _26_27 \ n |


После этого метод должен быть вызван в зависимости от ваших требований.

17
Ardent Coder 6 Июн 2020 в 06:28
2
Такой недооцененный ответ. все остальное немного вводит в заблуждение
 – 
csguy
13 Май 2019 в 05:17

То, что я заметил, помимо того, что next () сканирует только до пробела, тогда как nextLine () сканирует всю строку, это то, что next ждет, пока не получит полный токен , где, как nextLine () не ждет для полного токена, когда когда-либо получается '\ n' (т.е. когда вы нажимаете клавишу ввода), курсор сканера перемещается на следующую строку и возвращает предыдущую пропущенную строку. Он не проверяет, ввели ли вы полную input или нет, даже он будет принимать пустую строку, где, поскольку next () не принимает пустую строку

public class ScannerTest {

    public static void main(String[] args) {

        Scanner sc = new Scanner(System.in);
        int cases = sc.nextInt();
        String []str = new String[cases];
        for(int i=0;i<cases;i++){
            str[i]=sc.next();
        }
     }

}

Попробуйте эту программу, изменив next () и nextLine () в цикле for, продолжайте нажимать '\ n', то есть клавишу ввода без ввода, вы можете обнаружить, что с помощью метода nextLine () он завершается после нажатия заданного количества случаев, когда next () не завершается , пока вы не предоставите и не введете в него заданное количество случаев.

10
murali kurapati 28 Ноя 2018 в 22:55
1
Очень интересный пример. Запустив код, я наконец увидел, как next() работает на практике, он игнорирует клавишу ввода, тогда как nexLine() принимает его как полный ввод и реплицирует его на консоль, если вы повторяете значение того, что было захвачено. Я только что добавил System.out.println(str[i]); новой строкой под str[i]=sc.next(); или str[i]=sc.nextLine();
 – 
Pablo Adames
30 Сен 2019 в 01:30
Признателен, если вы можете проголосовать за ответ, если хотите
 – 
murali kurapati
1 Окт 2019 в 04:29

Вкратце: если вы вводите строковый массив длины t, то Scanner # nextLine () ожидает t строк, каждая запись в строковом массиве отличается от другой клавишей ввода. И Scanner # next () будет продолжать принимать входные данные до тех пор, пока вы нажимаете клавишу ВВОД, но сохраняете строку (слово) внутри массива, разделенную пробелом.

Давайте посмотрим на следующий фрагмент кода

    Scanner in = new Scanner(System.in);
    int t = in.nextInt();
    String[] s = new String[t];

    for (int i = 0; i < t; i++) {
        s[i] = in.next();
    }

Когда я запускаю приведенный выше фрагмент кода в своей среде IDE (скажем, для длины строки 2), не имеет значения, ввожу ли я свою строку как

Введите как: - abcd abcd или

Введите как: -

Abcd

Abcd

Вывод будет похож на abcd

Abcd

Но если в том же коде заменить метод next () на nextLine ()

    Scanner in = new Scanner(System.in);
    int t = in.nextInt();
    String[] s = new String[t];

    for (int i = 0; i < t; i++) {
        s[i] = in.nextLine();
    }

Затем, если вы введете ввод в командной строке как - abcd abcd

Выход: -

Abcd abcd

И если вы введете ввод в приглашении как abcd (и если вы нажмете Enter, чтобы ввести следующий abcd в другой строке, приглашение ввода просто выйдет, и вы получите результат)

Выход: -

Abcd

3
himani1349 8 Фев 2017 в 09:53

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

Next () используется для чтения отдельного слова, и когда он получает пробел, он прекращает чтение и курсор возвращается в исходное положение. NextLine () , в то время как эта функция читает все слово, даже если встречается с пробелом. Курсор останавливается, когда чтение закончено, и курсор возвращается в конец строки. поэтому вам не нужно использовать разделитель , когда вы хотите прочитать полное слово как предложение. вам просто нужно использовать NextLine ().

 public static void main(String[] args) {
            // TODO code application logic here
           String str;
            Scanner input = new Scanner( System.in );
            str=input.nextLine();
            System.out.println(str);
       }
0
Negash 6 Апр 2018 в 18:30

У меня тоже возникла проблема с разделителем. вопрос был о вводе

  1. введите ваше имя.
  2. введите свой возраст.
  3. введите адрес электронной почты.
  4. введите свой адрес.

Проблема

  1. Я успешно закончил, указав имя, возраст и адрес электронной почты.
  2. Когда я придумал адрес из двух слов, содержащих пробел (улица Харнет), я получил первое слово «харнет».

Решение

Я использовал разделитель для своего сканера и вышел успешно.

Пример

 public static void main (String args[]){
     //Initialize the Scanner this way so that it delimits input using a new line character.
    Scanner s = new Scanner(System.in).useDelimiter("\n");
    System.out.println("Enter Your Name: ");
    String name = s.next();
    System.out.println("Enter Your Age: ");
    int age = s.nextInt();
    System.out.println("Enter Your E-mail: ");
    String email = s.next();
    System.out.println("Enter Your Address: ");
    String address = s.next();

    System.out.println("Name: "+name);
    System.out.println("Age: "+age);
    System.out.println("E-mail: "+email);
    System.out.println("Address: "+address);
}
0
GabMic 6 Апр 2018 в 21:03

Основное отличие заключается в том, что next () используется для получения ввода до тех пор, пока не встретится разделитель (по умолчанию это пробел, но вы также можете его изменить) и возврата введенного вами токена. Курсор остается в той же строке. В то время как в nextLine () он сканирует ввод, пока мы не нажмем кнопку ввода, и не вернем все это целиком, и поместит курсор в следующую строку. **

        Scanner sc=new Scanner(System.in);
        String s[]=new String[2];
        for(int i=0;i<2;i++){
            s[i]=sc.next();
        }
        for(int j=0;j<2;j++)
        {
            System.out.println("The string at position "+j+ " is "+s[j]);
        }

**

Попробуйте запустить этот код, указав Input как «Hello World». Сканер считывает ввод до 'o', а затем появляется разделитель. Поэтому s [0] будет «Hello», а курсор будет указывать на следующую позицию после разделителя ( в нашем случае это 'W'), и когда s [1] считывается, он сканирует «Мир» и возвращает его в s [1] в качестве следующего полного токена (по определению Scanner). Если мы используем nextLine () вместо этого он будет читать «Hello World» полностью и даже больше, пока мы не нажмем кнопку ввода и не сохраним его в s [0]. Мы также можем указать другую строку, используя nextLine (). Я рекомендую вам попробовать использовать этот и другие примеры и попросить разъяснений.

0
Simple Coder 4 Авг 2019 в 09:08

Разница может быть очень очевидна с помощью приведенного ниже кода и его вывода.

    public static void main(String[] args) {
        List<String> arrayList = new ArrayList<>();
        List<String> arrayList2 = new ArrayList<>();
        Scanner input = new Scanner(System.in);

        String product = input.next();

        while(!product.equalsIgnoreCase("q")) {
            arrayList.add(product);
            product = input.next();
        }

        System.out.println("You wrote the following products \n");
        for (String naam : arrayList) {
            System.out.println(naam);
        }

        product = input.nextLine();
        System.out.println("Enter a product");
        while (!product.equalsIgnoreCase("q")) {
            arrayList2.add(product);
            System.out.println("Enter a product");
            product = input.nextLine();
        }

        System.out.println();
        System.out.println();
        System.out.println();
        System.out.println();

        System.out.println("You wrote the following products \n");
        for (String naam : arrayList2) {
            System.out.println(naam);
        }
    }

Вывод:

Enter a product
aaa aaa
Enter a product
Enter a product
bb
Enter a product
ccc cccc ccccc
Enter a product
Enter a product
Enter a product
q
You wrote the following products 

aaa
aaa
bb
ccc
cccc
ccccc
Enter a product
Enter a product
aaaa aaaa aaaa
Enter a product
bb
Enter a product
q




You wrote the following products 


aaaa aaaa aaaa
bb

Совершенно очевидно, что пробел-разделитель по умолчанию добавляет продукты, разделенные пробелом, в список, когда используется следующий, поэтому каждый раз, когда строки, разделенные пробелом, вводятся в строку, это разные строки. В nextLine пробел не имеет значения, и вся строка представляет собой одну строку.

-1
KnockingHeads 24 Май 2021 в 15:58

Методы next() [Существует несколько методов next(), таких как nextInt(), nextDouble() и т. д.] сканирование токенов (вы можете думать об этом как о слово), а метод nextLine() считывает текст из текущего местоположения сканера до начала следующей строки.

Я видел, что другие авторы также выделили это, поэтому я решил объяснить это на простом примере, чтобы продемонстрировать, как использовать их для предотвращения проблем с чтением ввода через стандартный ввод (стандартный поток ввода).

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

Когда вы вызываете функции Сканера, которые считывают токены (например, next(), nextInt(), nextDouble() и т. д.), Сканер считывает и возвращает следующий токен. Когда вы читаете всю строку (nextLine(),readLine()), она читается с текущей позиции до начала следующей строки. В результате, если между концом последней прочитанной строки и началом следующей строки нет символов, вызов nextLine() может вернуть пустую строку.

В качестве примера рассмотрим следующие входные данные:

a b c
d e
f
g

Следующие шаги иллюстрируют, как определенная последовательность вызовов объекта Scanner будет считывать введенные данные:

  1. Вызов scan.next(); возвращает следующий токен, a.
  2. Вызов scan.next(); возвращает следующий токен, b.
  3. Вызов scan.nextLine(); возвращает следующий токен, c. Важно отметить, что сканер возвращает пробел и букву, потому что он читает с конца последнего токена до начало следующей строки.
  4. Вызов scan.nextLine(); возвращает содержимое следующей строки, d e.
  5. Вызов scan.next(); возвращает следующий токен, f.
  6. Вызов scan.nextLine(); возвращает все после f до начала следующей строки; потому что там нет символов, это возвращает пустую строку.
  7. Вызов scan.nextLine(); возвращает г.

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

0
Dinindu Gunathilaka 11 Апр 2022 в 11:54