☕ Java
Scanner Class
The Scanner class (java.util.Scanner) is the standard way to read user input from the keyboard in Java. It wraps System.in and provides methods to parse tokens as specific types — nextInt(), nextDouble(), nextLine(), next() — without manually converting strings. Scanner also works with files and strings as input sources.
Creating a Scanner and Basic Reading
Scanner must be imported from java.util. For keyboard input, wrap System.in. Scanner reads tokens separated by whitespace (spaces, tabs, newlines) by default. Each next() or nextXxx() call reads the next token and advances the internal cursor. The Scanner should be closed when no longer needed, though closing System.in should be done carefully as it cannot be reopened.
Java
import java.util.Scanner;
public class BasicInput {
public static void main(String[] args) {
// ── Create Scanner for keyboard input: ───────────────────────
Scanner scanner = new Scanner(System.in);
// ── Read a String token (one word): ───────────────────────────
System.out.print("Enter your name: ");
String name = scanner.next(); // reads one word
System.out.println("Hello, " + name);
// ── Read an integer: ──────────────────────────────────────────
System.out.print("Enter your age: ");
int age = scanner.nextInt();
System.out.println("Age: " + age);
// ── Read a double: ────────────────────────────────────────────
System.out.print("Enter your height (m): ");
double height = scanner.nextDouble();
System.out.printf("Height: %.2f m%n", height);
// ── Read a boolean: ───────────────────────────────────────────
System.out.print("Active? (true/false): ");
boolean active = scanner.nextBoolean();
System.out.println("Active: " + active);
// ── Read a full line: ─────────────────────────────────────────
scanner.nextLine(); // consume leftover newline after nextBoolean()
System.out.print("Enter your address: ");
String address = scanner.nextLine(); // reads entire line
System.out.println("Address: " + address);
// ── Close scanner when done: ──────────────────────────────────
scanner.close();
}
}
// ── Input/Output example: ─────────────────────────────────────────────
// Enter your name: Alice
// Hello, Alice
// Enter your age: 30
// Age: 30
// Enter your height (m): 1.68
// Height: 1.68 m
// Active? (true/false): true
// Active: true
// Enter your address: 123 Main Street
// Address: 123 Main StreetScanner Methods Reference
Scanner provides a next method for each primitive type plus String. Each method has a corresponding hasNextXxx method that checks whether the next token can be read as that type without consuming it — essential for loops and validation.
Java
Scanner sc = new Scanner(System.in);
// ── Reading methods: ──────────────────────────────────────────────────
String word = sc.next(); // next whitespace-delimited token
String line = sc.nextLine(); // entire line including spaces
int i = sc.nextInt(); // next token as int
long l = sc.nextLong(); // next token as long
double d = sc.nextDouble(); // next token as double
float f = sc.nextFloat(); // next token as float
boolean b = sc.nextBoolean(); // next token as boolean (true/false)
byte by = sc.nextByte(); // next token as byte
short s = sc.nextShort(); // next token as short
// ── Checking methods (non-consuming): ────────────────────────────────
boolean hasToken = sc.hasNext(); // any token available?
boolean hasLine = sc.hasNextLine(); // any line available?
boolean hasInt = sc.hasNextInt(); // next token parseable as int?
boolean hasDouble = sc.hasNextDouble(); // next token parseable as double?
boolean hasBool = sc.hasNextBoolean(); // next token true or false?
// ── Validated input loop — keep asking until valid int: ───────────────
Scanner scanner = new Scanner(System.in);
int number = 0;
while (true) {
System.out.print("Enter an integer: ");
if (scanner.hasNextInt()) {
number = scanner.nextInt();
break;
} else {
System.out.println("Invalid — please enter a whole number.");
scanner.next(); // discard the invalid token
}
}
System.out.println("You entered: " + number);
// ── Read until end of input (file or piped input): ────────────────────
Scanner sc2 = new Scanner(System.in);
while (sc2.hasNextLine()) {
String inputLine = sc2.nextLine();
System.out.println("Read: " + inputLine);
}
// ── Read multiple values on one line: ────────────────────────────────
// Input: "Alice 30 1.68"
Scanner sc3 = new Scanner(System.in);
String n = sc3.next();
int a = sc3.nextInt();
double h = sc3.nextDouble();
System.out.printf("%s is %d years old and %.2fm tall%n", n, a, h);The nextLine() After nextInt() Problem
The most common Scanner pitfall occurs when mixing nextInt() (or any nextXxx() for primitives) with nextLine(). The nextInt() method reads the integer but leaves the newline character in the buffer. The immediately following nextLine() then reads that leftover newline instead of the next line of user input, returning an empty string. The fix is to call nextLine() once after nextInt() to consume the leftover newline before reading the next line.
Java
// ── The problem: nextLine() returns empty string: ────────────────────
Scanner sc = new Scanner(System.in);
System.out.print("Enter age: ");
int age = sc.nextInt();
// User types: 25 ↵
// Buffer after nextInt(): "
" ← leftover newline
System.out.print("Enter name: ");
String name = sc.nextLine();
// nextLine() reads up to the next
— finds the leftover
immediately
// Returns "" (empty string) without waiting for user input!
System.out.println("Age: " + age);
System.out.println("Name: '" + name + "'");
// Output:
// Enter age: 25
// Enter name: ← skipped! user never got to type
// Age: 25
// Name: '' ← empty!
// ── Fix 1: consume leftover newline with an extra nextLine(): ─────────
Scanner sc2 = new Scanner(System.in);
System.out.print("Enter age: ");
int age2 = sc2.nextInt();
sc2.nextLine(); // consume the leftover "
"
System.out.print("Enter name: ");
String name2 = sc2.nextLine(); // now reads correctly
System.out.println("Age: " + age2 + ", Name: " + name2);
// ── Fix 2: read everything as lines, then parse: ──────────────────────
Scanner sc3 = new Scanner(System.in);
System.out.print("Enter age: ");
int age3 = Integer.parseInt(sc3.nextLine().trim());
System.out.print("Enter name: ");
String name3 = sc3.nextLine(); // no problem — only using nextLine()
System.out.println("Age: " + age3 + ", Name: " + name3);
// ── Rule of thumb: ────────────────────────────────────────────────────
// Mixing nextInt()/nextDouble()/etc. with nextLine() in sequence
// always requires an extra nextLine() call in between.
// OR — use only nextLine() for all input and parse manually.Scanner with Files and Strings
Scanner is not limited to keyboard input. It can read from files, strings, and any InputStream. Reading from a file with Scanner is convenient for small files where token-based or line-by-line parsing is needed. Reading from a String is useful in tests and when parsing already-loaded content.
Java
import java.util.Scanner;
import java.io.File;
import java.io.FileNotFoundException;
// ── Scanner reading from a file: ─────────────────────────────────────
// data.txt contents:
// Alice 95
// Bob 87
// Charlie 72
try (Scanner fileScanner = new Scanner(new File("data.txt"))) {
while (fileScanner.hasNextLine()) {
String studentName = fileScanner.next();
int studentScore = fileScanner.nextInt();
System.out.printf("%-10s → %d%n", studentName, studentScore);
}
} catch (FileNotFoundException e) {
System.err.println("File not found: " + e.getMessage());
}
// Output:
// Alice → 95
// Bob → 87
// Charlie → 72
// ── Scanner with file using Path (Java 11+): ──────────────────────────
try (Scanner sc = new Scanner(Path.of("data.txt"))) {
while (sc.hasNextLine()) {
System.out.println(sc.nextLine());
}
} catch (IOException e) {
System.err.println("I/O error: " + e.getMessage());
}
// ── Scanner reading from a String: ───────────────────────────────────
String data = "10 20 30 40 50";
Scanner strScanner = new Scanner(data);
int sum = 0;
while (strScanner.hasNextInt()) {
sum += strScanner.nextInt();
}
System.out.println("Sum: " + sum); // Sum: 150
strScanner.close();
// ── Scanner with custom delimiter: ────────────────────────────────────
// Parse CSV line: "Alice,30,Engineer"
String csv = "Alice,30,Engineer";
Scanner csvScanner = new Scanner(csv).useDelimiter(",");
String csvName = csvScanner.next(); // Alice
int csvAge = csvScanner.nextInt(); // 30
String csvJob = csvScanner.next(); // Engineer
System.out.printf("%s (%d) — %s%n", csvName, csvAge, csvJob);
csvScanner.close();Related Topics in Java Basics
Logical Operators
Logical operators combine boolean expressions into more complex conditions. Java has six of them — short-circuit and non-short-circuit variants of AND, OR, and XOR, plus logical NOT. Understanding short-circuit evaluation is essential for writing both safe and efficient conditions.
Bitwise Operators
Bitwise operators work directly on the binary representation of integers — manipulating individual bits. They're used in low-level programming, performance-critical code, flags, masks, and cryptography. Understanding them requires thinking in binary, but the patterns they enable are concise and extremely fast.
Assignment Operators
Assignment operators store values into variables. Java has one basic assignment operator and eleven compound assignment operators that combine an operation with assignment. They're concise, but have specific type behavior — especially the implicit cast in compound assignments — that every Java developer needs to understand.
Unary Operators
Unary operators take a single operand. Java has five: unary plus, unary minus, increment, decrement, and logical NOT. The increment and decrement operators have prefix and postfix forms that behave differently — a distinction that trips up developers at every level.