Compact Source Files & Instance Main Methods practice questions

From OCP Java SE 25 (1Z0-831) · 15 questions on this topic

Compact Source Files & Instance Main Methods practice questions from OCP Java SE 25 (1Z0-831). This pack has 15 questions tagged Compact Source Files & Instance Main Methods, drawn from its timed mock exams. 8 of them are worked through in full below — the question, every option, why each is right or wrong, and the explanation.

Worked examples for Compact Source Files & Instance Main Methods

  1. Question 1

    java.lang.IO is the console API used by compact source files (and available everywhere). Which two of the following are valid calls that compile against the Java 25 IO class? (Choose two.)

    1. A. IO.println();Correct answer

      Correct: matches the no-arg println() overload, which prints just a line separator.

    2. B. IO.printf("%d%n", count);

      There is no printf on IO; formatted output still goes through System.out.printf or String.format. This is the single most common IO trap.

    3. C. IO.readln("Enter name: ");Correct answer

      Correct: matches readln(String), which prints the prompt and returns the line the user types.

    4. D. IO.print();

      print exists only as print(Object); there is no no-arg print(). Note the asymmetry: println has a no-arg form, print does not.

    Explanation

    The Java 25 java.lang.IO API is deliberately tiny — its whole surface is println(Object), a no-arg println(), print(Object), readln(), and readln(String). A call compiles only when it matches one of those five overloads; a call to a method that does not exist, such as printf or a no-arg print, does not. IO has no printf and no format, so formatted output must still go through System.out.printf or String.format.

  2. Question 2

    Both main methods here are instance methods; one takes String[], the other takes nothing. The class is compiled and run with java -cp . Main. What does it print?

    public class Main {
        void main(String[] args) { IO.println("chose args"); }
        void main() { IO.println("chose no-arg"); }
    }
    1. A. chose no-arg

      Reverses the priority; the no-arg form is the fallback, used only when there is no main(String[]).

    2. B. Compilation fails: the call to main is ambiguous

      The two overloads have different parameter lists, so there is no ambiguity; the launcher, not overload resolution, picks the entry point.

    3. C. chose args chose no-arg

      Only the single selected main runs; the other is never called by the launcher.

    4. D. chose argsCorrect answer

      Correct: both candidates are instance methods, so the static-versus-instance tie-breaker is irrelevant, and parameter shape decides — a main accepting String[] is preferred over a no-arg main.

    Explanation

    Both candidates are instance methods, so the static-versus-instance tie-breaker never applies. Parameter shape decides first: a main that accepts a String[] is preferred over a no-arg main, so that method is invoked. The launcher selects a single entry point rather than resolving an ambiguous overloaded call, and only the chosen method runs.

  3. Question 3

    This class mixes an instance field, a helper method, and an instance main. It is compiled with javac --release 25 and run with java -cp . Main. What does it print?

    public class Main {
        int base = 5;
        int plusThree(int n) { return n + 3; }
        void main() {
            IO.println("hi " + plusThree(base));
        }
    }
    1. A. hi 5

      Ignores the helper call; plusThree(5) is invoked and returns 8, not the raw field value.

    2. B. Compilation fails: an instance main may not read an instance field or call an instance method

      The opposite is true: being an instance method is precisely what gives main access to this, its fields, and its instance methods.

    3. C. hi 3

      Treats plusThree as if it returned the constant 3; it returns its argument plus 3, so plusThree(5) is 8.

    4. D. hi 8Correct answer

      Correct: the instance main runs on a real instance, so base (5) and the helper are available; plusThree(base) returns 5 + 3 = 8, and concatenation builds "hi " + 8.

    Explanation

    An instance main runs on a real instance of its class, so instance fields and helper methods are fully available through this. Here the field initialised to 5 is passed to the helper, which adds 3, and the result is concatenated into the printed string. Fields and helper methods are legal in both ordinary classes and compact source files.

  4. Question 4

    This class declares two main methods — one static with a parameter, one instance with none. It is compiled with javac --release 25 and run with java -cp . Main. What does it print?

    public class Main {
        static void main(String[] args) { IO.println("static with args"); }
        void main() { IO.println("instance no-arg"); }
    }
    1. A. instance no-arg

      The no-arg instance main is the lowest-priority candidate; it is chosen only when no main(String[]) exists.

    2. B. static with argsCorrect answer

      Correct: the two methods are legal overloads with distinct parameter lists, and the launcher prefers a main(String[]) over a no-arg main and a static candidate over an instance one, so static void main(String[] args) wins on both counts.

    3. C. Compilation fails: a class may not declare two methods both named main

      Overloading by parameter list is legal; the two main methods have distinct signatures, so the class compiles.

    4. D. static with args instance no-arg

      Exactly one main is selected and invoked; the launcher never runs both.

    Explanation

    The two methods have different parameter lists — main(String[]) versus main() — so they are legal overloads and the class compiles. The launcher then applies its selection order: a candidate accepting String[] is preferred over a no-arg one, and a static candidate is preferred over an instance one. A main(String[]) therefore outranks any no-arg main, and exactly one method is chosen and invoked.

  5. Question 5

    A file Calc.java contains only top-level fields, helper methods, and a void main() — there is no class declaration. It is launched with java Calc.java. Which statement is true?

    1. A. You may call println("x") unqualified, because the static methods of java.lang.IO are automatically imported into a compact source file.

      Measured false: Java 25 does not auto-import the static methods of IO; a bare println("x") fails with 'cannot find symbol'. Calls must be written IO.println("x").

    2. B. It will not run until you add public static void main(String[] args), the only entry point the launcher recognizes.

      The point of JEP 512 is that an instance and/or no-arg main is a legal entry point; the classic signature is not required.

    3. C. Its top-level fields and methods become members of an unnamed top-level class in the unnamed package, and main may be a non-public instance method.Correct answer

      Correct: JEP 512 treats the top-level members as an implicit unnamed top-level class in the unnamed package, launched via the flexible entry-point rules, so a package-private instance void main() is valid.

    4. D. Another source file can instantiate the implicit class with new Calc(), since it is named after the file.

      The implicit class has no name usable in source code, so no other class can name, import, or instantiate it, regardless of the file name.

    Explanation

    JEP 512 treats a compact source file's top-level members as members of an implicit, unnamed top-level class in the unnamed package, launched via the flexible entry-point rules, so a package-private instance main is a valid entry point. That class is real but nameless — no other source file can reference or instantiate it, whatever the file is called. And IO's static methods are not auto-imported, so calls to them must still be qualified.

  6. Question 6

    The file Greeter.java below is a compact source file (no class declaration) and is launched with java Greeter.java:

    String prefix = "Hi, ";
    
    Greeter() {
        prefix = "Hello, ";
    }
    
    void main() {
        IO.println(prefix + "world");
    }

    What happens?

    1. A. Prints Hi, world — the constructor compiles but is never called, so prefix keeps its initial value

      The declaration does not compile at all, so nothing prints; there is no compiled-but-uncalled constructor.

    2. B. Compilation fails: Greeter() is read as a method with no return type, which is illegal — an implicit class cannot declare a constructorCorrect answer

      Correct: the implicit class is unnamed, so a declaration with a name but no return type cannot be a constructor — the compiler parses Greeter() { ... } as a method missing its return type and rejects it, so the file never runs.

    3. C. Prints Hello, world — the implicit class is instantiated with Greeter() before main runs, so the constructor updates prefix

      The launcher instantiates the implicit class with its own implicit no-arg constructor; user code cannot supply one, and this declaration is rejected outright.

    4. D. Compilation fails: a compact source file may not declare instance fields such as prefix

      Fields (and helper methods) are explicitly allowed in a compact source file; only the named constructor is the problem here.

    Explanation

    A compact source file's top-level members belong to an implicit, unnamed class. Because that class has no name you can write, a declaration that has a name but no return type cannot be a constructor — the compiler parses it as a method missing its return type and rejects it with invalid method declaration; return type required, so the file never runs. Fields and helper methods are permitted in a compact source file; a constructor is not.

  7. Question 7

    Consider this class. Does it compile, and if so what does it print when run with java -cp . Main?

    public class Main {
        static void main() { IO.println("s"); }
        void main() { IO.println("i"); }
    }
    1. A. Compilation fails: main() is already defined in class MainCorrect answer

      Correct: static is not part of a method's signature, so static void main() and void main() share the identical signature main() — a duplicate-method declaration that javac rejects before any launch order is considered.

    2. B. Compiles and prints s, because a static main outranks an instance main

      The static-over-instance rule only applies to code that compiles; here the two signatures collide, so there is nothing to run.

    3. C. Compiles and prints i, because an instance main is preferred once one exists

      The same duplicate-signature problem prevents compilation, and the claimed instance-over-static priority is also backwards.

    4. D. Compiles and prints s then i, running both methods

      The code never compiles, and the launcher never runs two main methods anyway.

    Explanation

    Overloads are distinguished by their parameter lists, not by static. Both methods have the empty parameter list (), and because static is not part of a method's signature they share the same signature — a duplicate-method declaration that javac rejects with method main() is already defined in class Main. This differs from the legal main(String[])/main() pair, whose parameter lists genuinely differ.

  8. Question 8

    The file Report.java below is a compact source file (JEP 512) — it declares no class, and it contains no import statements at all. It is launched directly with java Report.java on JDK 25.

    List<Integer> scores = List.of(70, 85, 90);
    
    List<Integer> passing() {
        return scores.stream().filter(s -> s >= 80).toList();
    }
    
    void main() {
        IO.println("passed=" + passing());
    }

    What is the result?

    1. A. Compilation fails: IO lives in java.io and must be imported before it can be used.

      Misfiles the new console API: IO is java.lang.IO, so it needs no import anywhere — in a compact source file or an ordinary class — and the program compiles.

    2. B. passed=[70, 85, 90]

      The "filter does nothing until you collect" misconception; toList() is the terminal operation that consumes the filtered pipeline, not a plain conversion of the source list, so 70 is dropped.

    3. C. Compilation fails: cannot find symbol: class List — a compact source file still needs import java.util.List;.

      Incorrect for a compact source file: it gets an implicit import module java.base, so List resolves without an import line — that error would occur only if these lines were pasted into an ordinary class.

    4. D. passed=[85, 90]Correct answer

      Correct: a compact source file is compiled as if it began with import module java.base (pulling in java.util), and its top-level field and methods become members of an implicit class, so passing() filters to 85 and 90, printing passed=[85, 90].

    Explanation

    Trace: every compact source file is compiled as if it began with import module java.base;. That single implicit module import pulls in the exported packages of java.base — including java.util — so List and List.of resolve with no import line. scores is a top-level field, passing() is a top-level instance method, and both become members of the implicitly declared class, so passing() can read scores directly. The stream keeps 85 and 90 (both >= 80) and drops 70, and toList() renders as [85, 90], giving passed=[85, 90].

    Why the others are wrong: Compilation fails: cannot find symbol: class List ... encodes the belief that a compact source file gets only the ordinary java.lang auto-import, so java.util types must still be imported by hand. That is exactly the convenience JEP 512 removes — and the belief is correct for an ordinary class: paste these same lines into public class Report { ... } and javac really does report cannot find symbol: class List. The implicit module import is a property of the compact form, not of the file name. passed=[70, 85, 90] is the "filter does nothing until you collect" misconception — the student treats toList() as a plain conversion of the source list rather than the terminal operation that consumes the filtered pipeline. Compilation fails: IOlives injava.io ... is the very common misfiling of the new console API. IO is java.lang.IO, so it needs no import anywhere — in a compact source file or in an ordinary class.

    Exam tip: a compact source file gets two things an ordinary class does not — an implicit import module java.base and an implicitly declared class wrapping its top-level members. It does not get a static import of IO's methods, so you still write IO.println(...), never a bare println(...). Reverse trap: var is not allowed on a field, so a top-level var scores = List.of(...) in a compact source file fails with 'var' is not allowed here — top-level declarations are fields, not local variables.

Practice all 15 Compact Source Files & Instance Main Methods questions

OCP Java SE 25 has the full set, inside timed mock exams that mirror real exam conditions — every question with a worked explanation.

Drill 20 questions on Compact Source Files & Instance Main Methods →Open OCP Java SE 25 →

Other topics in this pack