Midterm review: weeks 1-9 mixed
A one-page summary of every topic on the midterm, from classes to exceptions, and 12 exam-style questions that mix the topics together.
This page is the last round before the midterm. Each of the first nine weeks can be asked separately, but midterm questions often combine two or three topics in one piece of code: a polymorphic call inside a constructor chain, an interface method in an abstract class, try/finally inside an overridden method. The table below collects the “if you do not know it, you lose points” rules of each week. After that there are 12 mixed questions; each question’s explanation says which week it belongs to. When you get stuck on a question, go back to that week’s page.
Study suggestion: solve the questions on paper, and do not open the answer before writing yours. In “What is printed?” questions, trace every line one by one and write the variable values next to it. In compile-error questions, first ask “does the compiler know this”: the compiler looks only at types, it does not see objects.
Weekly summary table
| Week | Topic | What you need to know | Classic pitfall |
|---|---|---|---|
| 1 | Classes and objects | Constructor, this, encapsulation, static and instance, toString, equals | name = name; does not fill the field; once you write a constructor the default constructor is gone |
| 2 | Inheritance | extends, super(...), constructor chain, overriding and overloading, Object | If the superclass has no no-argument constructor, the hidden super() does not compile |
| 3 | Polymorphism | Static type and dynamic type, upcasting, downcasting, instanceof | A method not in the type of the variable cannot be called; a wrong cast gives ClassCastException |
| 4 | Abstract and interface | abstract method, implements, default method, Comparable | Writing an interface method without public |
| 5 | GUI components | JFrame, JLabel, JTextField, JButton, FlowLayout, BorderLayout, GridLayout | The second add in BorderLayout replaces the previous one; getText() is a String |
| 6 | Events | ActionListener, getSource, inner class, anonymous class, lambda | Modifying a local variable inside a lambda |
| 7 | UML | Visibility markers, relationship arrows, multiplicity, aggregation and composition | The triangle points to the superclass; the diamond is on the whole side |
| 8 | String and regex | substring, indexOf, char arithmetic, StringBuilder, split, matches | If s.toUpperCase(); is not assigned, nothing changes |
| 9 | Exceptions | try/catch/finally flow, checked and unchecked, throw and throws, custom exception | Writing the general catch first; finally running before the return |
A method for solving output questions
In mixed questions, follow this order:
- If an object is created, draw the constructor chain. Starting from the top superclass, write the bodies in order. Do not forget that field initializers are assigned after
super()finishes. - Ask two questions at every method call. Does the compiler allow this call (type of the variable)? Which version runs at run time (type of the object)?
- If there is an overload, choose the signature first. Look at the compile-time types of the arguments.
- If an exception happens in a try, cross out the remaining lines. Find the first matching catch, add the finally, then go up if it was not caught.
- In String operations, write out the indexes. In
substringandindexOfquestions, number the characters from 0 underneath them.
Example: new Mid(); (Mid extends Base, show() is called inside Base())
1. Mid() → super() → Base()
2. Base body: "Base " then show()
3. show() is overridden, the object is a Mid → Mid.show() → tag is still null → "M.show(null) "
4. super() finished → Mid's fields are assigned: tag = "mid"
5. Mid body: "Mid "
Compile error or run-time error?
In “what happens?” questions on the midterm there are three answers: it does not compile, an exception is thrown while it runs, or it runs normally. A table to tell them apart:
| Situation | Result |
|---|---|
| Calling a method not in the type of the variable | Compile error |
| Assigning from a supertype to a subtype without a cast | Compile error |
| Cast between sibling classes | Compile error |
| A valid cast whose object does not fit | Run time: ClassCastException |
new on an abstract class | Compile error |
| A concrete class did not write an abstract method | Compile error |
| A checked exception neither caught nor declared | Compile error |
| Array or String bound exceeded | Run time: IndexOutOfBounds |
Method call on null | Run time: NullPointerException |
| Dividing an int by 0 | Run time: ArithmeticException |
Integer.parseInt("abc") | Run time: NumberFormatException |
| Modifying a local variable inside a lambda | Compile error |
| Access to a private field from another class | Compile error |
Final checklist
- When you override equals, is the parameter
Object? Did you write@Override? - Does the subclass constructor call the right constructor with
super(...)? - Did you write
publicwhen implementing interface methods? - Does compareTo return an int, did you use
Double.compareorInteger.compare? - Are the catches ordered from specific to general?
- Is your own exception
extends Exception(checked) orextends RuntimeException(unchecked), and does the method signature match? - Did you assign the String result to a variable?
Common mistakes
| Wrong idea | The truth |
|---|---|
| The subclass’s fields are ready at the start of the constructor | They hold default values until super() finishes |
equals(Coin c) overrides equals | It is an overload; when called with an argument of type Object, Object’s runs |
| An interface default method cannot be overridden | It can; the Final.grade() example |
p.parse("12") + p.parse("x") prints 12 first | println’s argument is computed completely, so the finally outputs come first |
| If there is a return in the catch, finally is skipped | It still runs |
| With an uncaught exception, finally does not run | It runs, then the exception goes up |
| An abstract class must write the interface method | It does not have to; the concrete subclass must |
Test yourself
Exam-style questions. Solve them on paper first, then reveal the answer.
What is printed?
class Item {
static int made = 0;
int id;
Item() { this(100); System.out.print("I() "); }
Item(int id) { this.id = id + made; made++; System.out.print("I(" + this.id + ") "); }
}
// in main:
new Item(); new Item(5);
System.out.println(Item.made);Show answer
new Item() → this(100): made is still 0, id = 100, made becomes 1, I(100) is printed; then the outer constructor prints I(). new Item(5): id = 5 + 1 = 6, made 2. The static counter was shared across the two objects. (Week 1)
What is printed by new Mid();?
class Base {
Base() { System.out.print("Base "); show(); }
void show() { System.out.print("B.show "); }
}
class Mid extends Base {
String tag = "mid";
Mid() { super(); System.out.print("Mid "); }
@Override void show() { System.out.print("M.show(" + tag + ") "); }
}Show answer
Base's constructor runs first. The show() inside it is overridden: the object is a Mid, so Mid's show runs. But Mid's field initializer (tag = "mid") is assigned after super() finishes; at that moment tag is still null. Then Mid's body. (Week 2 + 3)
What is printed?
interface Scorable {
int score();
default String grade() { return score() >= 50 ? "PASS" : "FAIL"; }
}
abstract class Exam implements Scorable {
protected int raw;
Exam(int raw) { this.raw = raw; }
public String toString() { return getClass().getSimpleName() + ":" + score() + ":" + grade(); }
}
class Midterm extends Exam { Midterm(int r) { super(r); } public int score() { return raw * 2; } }
class Final extends Exam {
Final(int r) { super(r); }
public int score() { return raw + 10; }
public String grade() { return score() >= 60 ? "PASS" : "FAIL"; }
}
// in main:
Exam[] exams = { new Midterm(30), new Final(45), new Midterm(20) };
for (Exam e : exams) System.out.println(e);Show answer
Midterm(30): 60, the default grade (threshold 50): PASS. Final(45): 55, Final overrides grade (threshold 60): FAIL. Midterm(20): 40 < 50: FAIL. Exam is abstract and does not write score; the concrete classes do. (Week 3 + 4)
Find the compile errors.
interface Scorable { int score(); }
abstract class Exam implements Scorable { }
class Quiz extends Exam { }
// in main:
Exam e = new Quiz();
Scorable s = e;
Quiz q = s;Show answer
Since Exam is abstract it does not have to write score(), but the concrete Quiz must: Quiz is not abstract and does not override abstract method score() in Scorable. Scorable s = e; is valid (upcasting). Quiz q = s; is a downcast: incompatible types: Scorable cannot be converted to Quiz; (Quiz) s is needed. (Week 3 + 4)
What is printed?
static String mystery(String s) {
StringBuilder sb = new StringBuilder();
for (int i = s.length() - 1; i >= 0; i -= 2) sb.append(s.charAt(i));
return sb.toString().toUpperCase();
}
// in main:
System.out.println(mystery("polymorph"));Show answer
"polymorph" has 9 characters, indexes 0-8. The loop goes 8, 6, 4, 2, 0: h, r, m, l, p. Joined it is "hrmlp", in upper case HRMLP. (Week 8)
What is printed?
String s = "a-b--c";
System.out.println(s.split("-").length + " " + s.replaceAll("-+", "+") + " " + s.indexOf("--"));Show answer
split: a, b, "" (between the two dashes), c: 4 parts. -+ is one or more dashes: each group becomes a single +. "--" first starts at index 3 (a0 -1 b2 -3). (Week 8)
What is printed?
class Parser { int parse(String s) { return Integer.parseInt(s); } }
class SafeParser extends Parser {
@Override int parse(String s) {
try { return super.parse(s); }
catch (NumberFormatException e) { return -1; }
finally { System.out.print("[done " + s + "] "); }
}
}
// in main:
Parser p = new SafeParser();
System.out.println(p.parse("12") + p.parse("x"));Show answer
Dynamic binding: both calls go to SafeParser's parse. "12" → 12, finally prints. "x" → NumberFormatException is caught, −1, finally prints. println's argument is computed only after both calls finish: 12 + (−1) = 11 is printed last. (Week 3 + 9)
What is printed?
static int risky(int x) {
try {
if (x < 0) throw new IllegalArgumentException("neg");
return 10 / x;
} catch (ArithmeticException e) {
System.out.print("AE ");
return 0;
} finally {
System.out.print("F ");
}
}
// in main:
System.out.println(risky(5));
System.out.println(risky(0));
try { System.out.println(risky(-1)); }
catch (IllegalArgumentException e) { System.out.println("caught " + e.getMessage()); }Show answer
risky(5): 10 / 5 = 2, before returning, finally prints "F ". risky(0): ArithmeticException is caught, "AE ", it will return 0, but first finally prints "F ". risky(-1): there is no catch for IllegalArgumentException; finally runs, the exception goes up to main and the catch there catches it. (Week 9)
What is printed?
class Coin {
int value;
Coin(int v) { value = v; }
public boolean equals(Coin other) { return value == other.value; }
}
// in main:
Coin c1 = new Coin(5), c2 = new Coin(5);
Object o2 = c2;
System.out.println(c1.equals(c2) + " " + c1.equals(o2));Show answer
equals(Coin) does not override Object's equals(Object), it overloads it. c1.equals(c2): the argument is a Coin, the compiler chooses equals(Coin): true. c1.equals(o2): the static type of the argument is Object, equals(Object) is chosen, and that is Object's (address): false. If @Override had been written, the compiler would have caught the error. (Week 1 + 2 + 3)
Which statement is FALSE?
- A subclass constructor always calls a superclass constructor first
- An interface can contain default methods
- A checked exception must be caught or declared
- Fields are chosen by the object's runtime type
Show answer
Fields are not overridden; ref.field looks at the compile-time type of the variable. Dynamic binding is only for overridden instance methods. The other three are true: the hidden super(), Java 8+ default methods, the checked exception rule.
Which layout is the default for a JFrame's content pane, and what happens when you call frame.add(b1); frame.add(b2);?
Show answer
The content pane comes with BorderLayout; an add without a position puts the component in CENTER and replaces the earlier component in the same region. To see them side by side, use setLayout(new FlowLayout()) or a JPanel. (Week 5)
Write an abstract class Shape that implements Comparable<Shape> (comparing by area) with an abstract double area(), and two subclasses Rect(w, h) and Circle(r). Sorting {Rect(2,5), Circle(1), Rect(1,1)} must give [Rect(1.0), Circle(3.14), Rect(10.0)].
Show answer
compareTo is written once in the abstract class, and the area() inside it works differently in each subclass (polymorphism):
abstract class Shape implements Comparable<Shape> {
abstract double area();
public int compareTo(Shape o) {
return Double.compare(area(), o.area());
}
}
class Rect extends Shape {
double w, h;
Rect(double w, double h) { this.w = w; this.h = h; }
double area() { return w * h; }
public String toString() { return "Rect(" + area() + ")"; }
}
class Circle extends Shape {
double r;
Circle(double r) { this.r = r; }
double area() { return Math.PI * r * r; }
public String toString() { return String.format("Circle(%.2f)", area()); }
}The areas are 10.0, 3.14..., 1.0; Arrays.sort orders them ascending: [Rect(1.0), Circle(3.14), Rect(10.0)].Verification: All questions were run with JDK 26 (java verify/SEN1002/W10.java); the compile-error question was tried with javac (verify/SEN1002/err/E10a.java). The rules in the summary table come from the verification files of the week 1-9 pages.