JavaRush /Blog Java /Random-PL /Klasa skanera w Javie

Klasa skanera w Javie

Opublikowano w grupie Random-PL
Cześć! Nasza dzisiejsza lekcja będzie wyjątkowa! Wcześniej przy rozwiązywaniu problemów i pisaniu programów algorytm był prosty: piszemy jakiś kod, uruchamiamy metodę main() , program robi to, co jest od niego wymagane i wychodzi. Ale teraz wszystko się zmieni! Dziś nauczymy się jak naprawdę współdziałać z programem: nauczymy go reagować na nasze działania! Być może już rozumiesz, dokąd w tym zmierzamy. Ten wykład poświęcimy szczegółowej analizie jednej z klas języka Java – Scanner. Klasa ta przyda się, jeśli zajdzie potrzeba odczytania danych wprowadzanych przez użytkowników. Zanim przejdziemy do nauki kodu, powiedz mi, czy kiedykolwiek spotkałeś się z takim urządzeniem jak skaner? Z pewnością tak. Wewnętrzna budowa skanera jest dość złożona, ale istota jego działania jest dość prosta: odczytuje dane, które wprowadza do niego użytkownik (np. paszport czy polisa ubezpieczeniowa) i zapisuje odczytane informacje w pamięci (np. w formie obrazu). Więc dzisiaj stworzysz swój własny skaner! Dokumentów oczywiście nie radzi sobie, ale z informacjami tekstowymi radzi sobie całkiem nieźle :) Do dzieła!Klasa skanera - 1

Klasa skanera Java

Pierwszą i najważniejszą rzeczą, z którą musimy się zapoznać, są zajęcia java.util.Scanner. Jego funkcjonalność jest bardzo prosta. Podobnie jak prawdziwy skaner, odczytuje dane ze wskazanego dla niego źródła. Na przykład z linii, z pliku, z konsoli. Następnie rozpoznaje te informacje i przetwarza je według potrzeb. Podajmy najprostszy przykład:
public class Main {

   public static void main(String[] args) {

       Scanner scanner = new Scanner(„Kocham cię, stworzenie Petry,\n” +
               „Uwielbiam twój surowy, smukły wygląd\n” +
               "Suwerenny prąd Newy,\n" +
               „Nadmorski granit”);
       String s = scanner.nextLine();
       System.out.println(s);
   }
}
Stworzyliśmy obiekt skanera i określiliśmy dla niego źródło danych (ciąg znaków z tekstem). Metoda nextLine()uzyskuje dostęp do źródła danych (nasz tekst z czterowierszami), znajduje tam kolejną linię, której jeszcze nie przeczytała (w naszym przypadku pierwszą) i zwraca ją. Następnie wyprowadzamy go na konsolę: Dane wyjściowe konsoli:

Люблю тебя, Piotrа творенье,
Możemy zastosować tę metodę nextLine()kilka razy i wypisać cały fragment wiersza:
public class Main {

   public static void main(String[] args) {

       Scanner scanner = new Scanner(„Kocham cię, stworzenie Petry,\n” +
               „Uwielbiam twój surowy, smukły wygląd\n” +
               "Suwerenny prąd Newy,\n" +
               „Nadmorski granit”);
       String s = scanner.nextLine();
       System.out.println(s);
       s = scanner.nextLine();
       System.out.println(s);
       s = scanner.nextLine();
       System.out.println(s);
       s = scanner.nextLine();
       System.out.println(s);
   }
}
Za każdym razem nasz skaner zrobi krok do przodu i przeczyta kolejną linijkę. Wynik działania programu jest wysyłany do konsoli:

Люблю тебя, Piotrа творенье,
Люблю твой строгий, стройный вид,
Невы державное теченье,
Береговой ее гранит
Jak już powiedzieliśmy, źródłem danych dla skanera może być nie tylko ciąg znaków, ale także np. konsola. Ważna dla nas wiadomość: jeśli wcześniej wprowadzaliśmy tam tylko dane, teraz będziemy wprowadzać dane z klawiatury! Zobaczmy, co jeszcze potrafi klasa Scanner :
public class Main {

   public static void main(String[] args) {

       Scanner sc = new Scanner(System.in);
       System.out.println(„Wprowadź numer:”);

       int number = sc.nextInt();

       System.out.println("Dziękujemy! Wpisałeś numer" + number);

   }
}
Metoda nextInt()odczytuje i zwraca wprowadzoną liczbę. W naszym programie służy do przypisania wartości zmiennej number. To bardziej przypomina prawdziwy skaner! Program prosi użytkownika o wpisanie dowolnej liczby w wierszu. Gdy użytkownik to zrobi, program mu dziękuje, wyświetla wynik swojej pracy na konsoli i kończy się. Ale nadal mamy jeden poważny problem. Użytkownik może popełnić błąd i wprowadzić coś błędnego. Oto przykład sytuacji, w której nasz bieżący program przestanie działać:
public class Main {

   public static void main(String[] args) {

       Scanner sc = new Scanner(System.in);
       System.out.println(„Wprowadź numer:”);

       int number = sc.nextInt();

       System.out.println("Dziękujemy! Wpisałeś numer" + number);

   }
}
Spróbujmy wpisać ciąg „JavaRush” zamiast liczby: Dane wyjściowe konsoli:
Wpisz numer:
JavaRush
Exception in thread "main" java.util.InputMismatchException
  at java.util.Scanner.throwFor(Scanner.java:864)
  at java.util.Scanner.next(Scanner.java:1485)
  at java.util.Scanner.nextInt(Scanner.java:2117)
  at java.util.Scanner.nextInt(Scanner.java:2076)
  at Main.main(Main.java:10)

Process finished with exit code 1
Ups, wszystko jest źle -_- Aby uniknąć takich sytuacji, musimy wymyślić sposób na walidację danych wprowadzanych przez użytkownika. Przykładowo, jeśli użytkownik wpisze coś innego niż cyfrę, dobrze byłoby wyświetlić w konsoli ostrzeżenie, że wpisana informacja nie jest liczbą, a jeśli wszystko się zgadza, wyświetlić tekst potwierdzenia. Ale żeby to zrobić, tak naprawdę musimy „spojrzeć w przyszłość” – dowiedzieć się, co będzie dalej w naszym przepływie. Czy skaner w Javie może to zrobić? Jak on może! I do tego ma całą grupę metod: hasNextInt()- metoda sprawdza, czy kolejna część wprowadzonych danych jest liczbą, czy nie (zwraca odpowiednio wartość true lub false). hasNextLine()— sprawdza, czy następna część danych jest ciągiem znaków. hasNextByte(), hasNextShort(), hasNextLong(), hasNextFloat(), hasNextDouble()- wszystkie te metody robią to samo dla innych typów danych. Spróbujmy zmienić nasz program na czytanie liczb:
public class Main {

   public static void main(String[] args) {

       Scanner sc = new Scanner(System.in);
       System.out.println(„Wprowadź numer:”);

       if (sc.hasNextInt()) {
           int number = sc.nextInt();
           System.out.println("Dziękujemy! Wpisałeś numer" + number);
       } else {
           System.out.println(„Przepraszamy, ale to z pewnością nie jest liczba. Uruchom ponownie program i spróbuj ponownie!”);
       }

   }
}
Teraz nasz program sprawdza, czy następny wprowadzony znak jest liczbą, czy nie. I tylko jeśli tak jest, wyświetla potwierdzenie. Jeśli dane wejściowe nie przejdą testu, program to zauważy i poprosi o ponowną próbę. Zasadniczo możesz komunikować się z obiektem Scanner i wiedzieć z góry, jakiego rodzaju danych się spodziewać. „Hej, skanerze, co dalej? Liczba, ciąg znaków czy coś innego? Numer? A który - int, short, long?” Ta elastyczność daje możliwość budowania logiki programu w zależności od zachowań użytkownika. Kolejną ważną metodą, na którą warto zwrócić uwagę, jest useDelimiter(). Do tej metody przekazywany jest ciąg, którego chcesz użyć jako ogranicznika. Na przykład nagle zainteresowaliśmy się poezją japońską i postanowiliśmy użyć skanera, aby przeczytać kilka haiku wielkiego poety Matsuo Basho. Nawet jeśli w jednej niezgrabnej linijce podano nam trzy różne wersety, możemy je łatwo rozdzielić i ładnie sformatować:
public class Main {
   public static void main(String[] args) {
       Scanner scan = new Scanner(„Na gołej gałęzi” +
               „Kruk siedzi sam”. +
               „Jesienny wieczór”. +
               "''***''" +
               „Jest taki księżyc na niebie” +
               „Jak drzewo ścięte u korzeni:” +
               „Świeże cięcie staje się białe”. +
               "''***''" +
               „Jak ta rzeka się wylała!” +
               „Czapla wędruje na krótkich nogach” +
               „W wodzie po kolana”.);

       scan.useDelimiter("'");

       while (scan.hasNext()) {
           System.out.println(scan.next());
       }

       scan.close();
   }
}
Jako separatora linii używamy metody useDelimeter() klasy Scanner : odpowiada ona za dzielenie przychodzących danych na części. W naszym przypadku pojedynczy cudzysłów ( „'” ) jest przekazywany jako argument i używany do oddzielania ciągów znaków . Tekst następujący po tym cudzysłowie pojawia się w nowej linii, ponieważ w pętli while do odczytu danych używamy metody println() klasy System . W rezultacie będziemy mieli piękny wynik w konsoli, tak jak w książkach:
На голой ветке
Ворон сидит одиноко.
Осенний вечер.

*** 
 
В небе такая луна,
Словно дерево спилено под корень:
Белеет свежий срез.

*** 
 
Как разлилась река!
Цапля бредет на коротких ножках,
По колено в воде.
W tym samym przykładzie jest jeszcze jedna metoda, na którą zdecydowanie powinieneś zwrócić uwagę - close(). Jak każdy obiekt współpracujący ze strumieniami I/O, skaner po zakończeniu swojej pracy powinien zostać zamknięty, aby nie zużywał już zasobów naszego komputera. Nigdy nie zapominaj o metodzie close()!
public class Main {

   public static void main(String[] args) {

       Scanner sc = new Scanner(System.in);
       System.out.println(„Wprowadź numer:”);

       int number = sc.nextInt();

       System.out.println("Dziękujemy! Wpisałeś numer" + number);

       sc.close();//Teraz zrobiliśmy wszystko dobrze!

   }
}
To wszystko! Jak widać, klasa Scanner jest dość łatwa w użyciu i bardzo przydatna! :)
Komentarze
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION