What this quiz covers
This quiz focuses on Anatomy Of A Class, giving you a quick way to practice the rules, question types, and explanations that matter most for AP Computer Science a.
Considering the Java class example below, which access modifier would you use for owner to ensure encapsulation?
public class BankAccount {
// Fields represent state
private String owner;
private double balance;
public BankAccount(String owner, double startingBalance) {
this.owner = owner;
balance = startingBalance;
}
public String getOwner() { return owner; }
}
// Encapsulation: hide fields, expose methods.
// Inheritance: subclasses can extend BankAccount.
// Polymorphism: overridden methods can change behavior.
Based on the class structure presented above, which modifier best fits owner?
AP Computer Science a Quiz
Practice Anatomy Of A Class in AP Computer Science a with focused quiz questions that help you check what you know, review explanations, and build confidence with test-style prompts.
This quiz focuses on Anatomy Of A Class, giving you a quick way to practice the rules, question types, and explanations that matter most for AP Computer Science a.
Try each quiz question before looking at the correct answer. Use the explanations to review missed ideas, then come back to similar questions until the pattern feels familiar.
Considering the Java class example below, which access modifier would you use for owner to ensure encapsulation?
public class BankAccount {
// Fields represent state
private String owner;
private double balance;
public BankAccount(String owner, double startingBalance) {
this.owner = owner;
balance = startingBalance;
}
public String getOwner() { return owner; }
}
// Encapsulation: hide fields, expose methods.
// Inheritance: subclasses can extend BankAccount.
// Polymorphism: overridden methods can change behavior.
Based on the class structure presented above, which modifier best fits owner?
Explanation: This question tests AP Computer Science A understanding of access modifiers and encapsulation best practices. The principle of encapsulation dictates that fields should be private to prevent direct external access, with public methods providing controlled access when needed. In the BankAccount class, the owner field contains sensitive account information that should be protected from direct modification, while the getOwner() method provides read-only access. Choice C is correct because private access ensures that only the BankAccount class itself can directly access the owner field, maintaining data integrity and allowing future implementation changes without affecting client code. Choice A is incorrect because protected access would allow any class in the same package or subclasses to modify owner directly, weakening encapsulation. Students should understand that private fields with public getters (and setters when needed) represent the standard Java pattern. Practice identifying which fields need protection and writing appropriate access methods.
Considering the Java class example below, how does inheritance benefit the class structure?
public class Animal {
private String name;
public Animal(String name) {
this.name = name;
}
public String getName() { return name; }
public void speak() {
System.out.println("...");
}
}
public class Dog extends Animal {
public Dog(String name) { super(name); }
@Override
public void speak() {
System.out.println("Woof");
}
}
// Encapsulation: name is private and accessed via getName().
// Inheritance: Dog reuses Animal code.
// Polymorphism: speak() can vary by subclass.
Based on the class structure presented above, how does inheritance benefit this design?
Explanation: This question tests AP Computer Science A understanding of inheritance benefits in object-oriented design. Inheritance creates an 'is-a' relationship where subclasses automatically inherit accessible fields and methods from their superclass, promoting code reuse and establishing logical hierarchies. In the example, Dog extends Animal and inherits the private name field (accessed through getName()) and the speak() method, while only needing to implement Dog-specific behavior like the overridden speak() method. Choice A is correct because it accurately identifies that Dog reuses Animal's fields and methods without rewriting them, demonstrating the primary benefit of inheritance. Choice B is incorrect because inheritance actually enables method overriding (as shown with speak()), not prevents it, which is a fundamental aspect of polymorphism. Teachers should emphasize the super() call in constructors and how inherited members work. Use UML diagrams to visualize inheritance relationships and practice identifying what is inherited versus what must be implemented in subclasses.
Considering the Java class example below, which access modifier best ensures encapsulation for balance?
// BankAccount models a simple account for AP CSA
public class BankAccount {
// Fields store object state
private String owner;
private double balance;
// Constructor initializes fields
public BankAccount(String owner, double startingBalance) {
this.owner = owner;
balance = startingBalance;
}
// Methods provide controlled access/behavior
public void deposit(double amount) {
if (amount > 0) balance += amount;
}
public boolean withdraw(double amount) {
if (amount > 0 && amount <= balance) {
balance -= amount;
return true;
}
return false;
}
public double getBalance() { return balance; }
}
// Encapsulation keeps fields hidden and uses public methods.
// Inheritance lets a class extend another class.
// Polymorphism lets overridden methods run based on object type.
Based on the class structure presented above, which modifier should balance use?
Explanation: This question tests AP Computer Science A understanding of access modifiers and encapsulation principles in Java class design. Encapsulation is a fundamental OOP principle that protects data by restricting direct access to fields and providing controlled access through methods. In the BankAccount class, the balance field stores sensitive financial data that should only be modified through validated methods like deposit() and withdraw(). Choice C is correct because the private modifier ensures that balance can only be accessed within the BankAccount class itself, preventing external classes from directly manipulating this critical data. Choice A (public) is incorrect because it would allow any class to directly modify balance without validation, breaking encapsulation and potentially causing data corruption. Students should understand that private fields with public getter/setter methods represent the standard pattern for encapsulation in Java. Practice identifying which data needs protection and writing appropriate accessor methods to reinforce this concept.
Considering the Java class example below, which statement best describes polymorphism?
public class Animal {
public void speak() {
System.out.println("...");
}
}
public class Dog extends Animal {
@Override
public void speak() {
System.out.println("Woof");
}
}
public class Cat extends Animal {
@Override
public void speak() {
System.out.println("Meow");
}
}
class Demo {
public static void main(String[] args) {
Animal a1 = new Dog();
Animal a2 = new Cat();
a1.speak();
a2.speak();
}
}
// Encapsulation: hide fields using private.
// Inheritance: Dog and Cat extend Animal.
// Polymorphism: the same call can run different overridden methods.
Based on the class structure presented above, which best describes polymorphism here?
Explanation: This question tests AP Computer Science A understanding of polymorphism and method overriding in inheritance hierarchies. Polymorphism allows a single method call to execute different implementations based on the actual object type at runtime, enabling flexible and extensible code design. In the example, Animal references (a1 and a2) point to Dog and Cat objects respectively, and when speak() is called, Java's dynamic binding executes the overridden version in each subclass, printing 'Woof' and 'Meow' instead of '...'. Choice A is correct because it accurately describes how polymorphism enables one method call to run different overridden versions based on the actual object type. Choice C is incorrect because it confuses polymorphism with method overloading (multiple methods with the same name but different parameters), which is a compile-time feature rather than runtime behavior. Students should trace through code execution to see how the same method call produces different results. Use visual representations showing how method calls are resolved at runtime based on object type, not reference type.
Considering the Java class example below, which of the following best describes polymorphism as applied?
// Animal is a superclass.
public class Animal {
public void speak() {
System.out.println("...");
}
}
// Dog overrides speak().
public class Dog extends Animal {
@Override
public void speak() {
System.out.println("Woof");
}
}
// Cat overrides speak().
public class Cat extends Animal {
@Override
public void speak() {
System.out.println("Meow");
}
}
// Polymorphism: same method call, different behavior.
public class Demo {
public static void main(String[] args) {
Animal a1 = new Dog();
Animal a2 = new Cat();
a1.speak(); // calls Dog version
a2.speak(); // calls Cat version
}
}
// Encapsulation: keep fields private, expose methods.
// Inheritance: Dog and Cat reuse Animal structure.
Based on the class structure presented above, which of the following best describes polymorphism as applied in the 'Dog' and 'Cat' classes?
Explanation: This question tests AP Computer Science A understanding of polymorphism and method overriding in object-oriented programming. Polymorphism allows objects of different types to be treated uniformly through a common interface, enabling the same method call to produce different behaviors based on the actual object type at runtime. In the example, Animal references (a1 and a2) can point to Dog and Cat objects, and when speak() is called, Java's dynamic binding ensures the overridden version in the actual object type executes. Choice B is correct because it accurately describes how polymorphism works: calling speak() on Animal references executes the overridden methods in the subclasses, demonstrating 'one interface, multiple implementations.' Choice A is incorrect because it describes method overloading (multiple constructors with different parameters), not polymorphism. Teachers should use visual demonstrations showing how the same Animal reference can exhibit different behaviors, reinforcing that polymorphism enables flexible, extensible code design.
Considering the Java class example below, what is the purpose of the constructor?
public class Car {
// Fields (state)
private String make;
private String model;
private int year;
// Constructor
public Car(String make, String model, int year) {
this.make = make;
this.model = model;
this.year = year;
}
// Methods (behavior)
public void start() { /* start engine */ }
public void stop() { /* stop engine */ }
}
// Encapsulation: fields are private; methods are public.
// Inheritance: a class can extend another class.
// Polymorphism: overridden methods run based on object type.
Based on the class structure presented above, what is the constructor's purpose?
Explanation: This question tests AP Computer Science A understanding of constructors and their role in object initialization. Constructors are special methods that execute when objects are created using the 'new' keyword, setting up the initial state of an object by assigning values to its fields. In the Car class example, the constructor takes three parameters (make, model, year) and uses them to initialize the corresponding private fields, ensuring every Car object starts with meaningful data. Choice A is correct because it accurately describes the constructor's primary purpose of initializing fields when an object is instantiated. Choice C is incorrect because it confuses constructors with destructors (which don't exist in Java due to automatic garbage collection), a common misconception among students learning from C++ backgrounds. Teachers should emphasize that constructors have the same name as the class, no return type, and execute automatically during object creation. Use memory diagrams to show how constructors set up object state and practice writing constructors with different parameter lists.
Considering the Java class example below, why is it important to use methods like start() in a class structure?
public class Car {
private boolean running;
public Car() {
running = false; // constructor sets initial state
}
public void start() {
// behavior changes state safely
running = true;
}
public void stop() {
running = false;
}
}
// Encapsulation: running is private; methods change it.
// Inheritance: a subclass could extend Car.
// Polymorphism: a subclass could override start().
Based on the class structure presented above, why use methods like start()?
Explanation: This question tests AP Computer Science A understanding of methods as the behavior component of classes and their role in encapsulation. Methods like start() encapsulate behavior that safely modifies an object's private state, ensuring that state changes follow defined rules and maintaining object consistency. In the Car class, start() provides a controlled way to change the private running field from false to true, representing the car's engine state in a meaningful way. Choice A is correct because it identifies that methods provide behavior that updates private state, which is fundamental to object-oriented design where objects have both state (fields) and behavior (methods). Choice C is incorrect because methods complement constructors rather than replace them - constructors initialize state while methods modify it during the object's lifetime. Teachers should emphasize that methods represent what objects can do, while fields represent what objects know. Use real-world analogies and have students design classes where methods model realistic behaviors.
Considering the Java class example below, how does inheritance benefit the class structure illustrated?
public class Animal {
public void eat() {
System.out.println("Eating");
}
}
public class Dog extends Animal {
public void fetch() {
System.out.println("Fetching");
}
}
// Encapsulation: fields would be private (not shown).
// Inheritance: Dog gets eat() without rewriting it.
// Polymorphism: overridden methods can vary (not shown).
Based on the class structure presented above, how does inheritance help Dog?
Explanation: This question tests AP Computer Science A understanding of inheritance and code reuse in class hierarchies. Inheritance allows subclasses to automatically acquire non-private members from their superclass without rewriting code, following the DRY (Don't Repeat Yourself) principle. In the example, Dog extends Animal and automatically inherits the eat() method, so Dog objects can call eat() without the method being defined in the Dog class itself. Choice A is correct because it accurately states that Dog automatically gains the eat() method from Animal through inheritance. Choice C is incorrect because inherited methods don't need to be redefined unless you want different behavior - the code compiles and runs perfectly with Dog using Animal's eat() implementation. Students should understand the difference between inheriting a method and overriding it. Practice creating inheritance hierarchies and testing which methods are available in subclasses to reinforce automatic inheritance of non-private members.
Considering the Java class example below, which of the following best describes polymorphism as applied?
public class Animal {
public void speak() { System.out.println("..."); }
}
public class Dog extends Animal {
@Override
public void speak() { System.out.println("Woof"); }
}
public class Cat extends Animal {
@Override
public void speak() { System.out.println("Meow"); }
}
class Test {
public static void makeItSpeak(Animal a) {
a.speak(); // same call, different results
}
}
// Encapsulation: fields (if any) stay private.
// Inheritance: Dog/Cat extend Animal.
// Polymorphism: Animal reference can call subclass overrides.
Based on the class structure presented above, which choice best describes polymorphism?
Explanation: This question tests AP Computer Science A understanding of polymorphism as a core object-oriented principle. Polymorphism allows a single reference type to exhibit multiple behaviors through method overriding, where the actual behavior depends on the object's runtime type, not its compile-time reference type. In the example, the makeItSpeak() method accepts an Animal reference but can invoke Dog's or Cat's overridden speak() method, demonstrating how one interface supports many implementations. Choice B is correct because it accurately describes polymorphism as allowing one reference type (Animal) to use many behaviors (different speak() implementations). Choice A is incorrect because it describes name conflicts or overloading rather than polymorphism - polymorphism is about behavior variation, not naming. Teachers should trace through code execution showing how the same method call produces different outputs. Use debugging tools to show students how Java determines which method to call at runtime based on the actual object type.
Considering the Java class example below, what is the purpose of the constructor?
public class Student {
// Fields
private String name;
private int gradeLevel;
// Constructor
public Student(String name, int gradeLevel) {
this.name = name;
this.gradeLevel = gradeLevel;
}
// Method
public String getName() { return name; }
}
// Encapsulation: private fields, public getters.
// Inheritance: a class can extend Student (not shown).
// Polymorphism: overridden methods can vary (not shown).
Based on the class structure presented above, what does the constructor do?
Explanation: This question tests AP Computer Science A understanding of constructor functionality in object initialization. Constructors are special methods that run automatically when objects are created, setting up the initial state by assigning values to instance fields. In the Student class, the constructor takes name and gradeLevel parameters and uses the 'this' keyword to distinguish between parameters and instance fields with the same names, ensuring proper initialization. Choice A is correct because it accurately describes that the constructor initializes the name and gradeLevel fields for new Student objects. Choice D is incorrect because constructors enable object creation rather than prevent it - a class without accessible constructors would prevent instantiation, which is the opposite of this constructor's purpose. Teachers should emphasize the difference between declaring fields and initializing them in constructors. Practice using the 'this' keyword and explain how constructors differ from regular methods in syntax and purpose.
Considering the Java class example below, why is it important to use methods like withdraw()?
public class BankAccount {
private String owner;
private double balance;
public BankAccount(String owner, double startingBalance) {
this.owner = owner;
balance = startingBalance;
}
public boolean withdraw(double amount) {
// Controlled update to state
if (amount > 0 && amount <= balance) {
balance -= amount;
return true;
}
return false;
}
public double getBalance() { return balance; }
}
// Encapsulation: methods control how balance changes.
// Inheritance: classes can extend BankAccount (not shown).
// Polymorphism: overridden methods can change behavior (not shown).
Based on the class structure presented above, why use methods like withdraw()?
Explanation: This question tests AP Computer Science A understanding of encapsulation and the importance of controlled access to object state. Methods like withdraw() serve as gatekeepers that validate and control how an object's internal state changes, maintaining data integrity and enforcing business rules. In the BankAccount example, withdraw() prevents invalid operations by checking that the amount is positive and doesn't exceed the balance, returning a boolean to indicate success or failure. Choice A is correct because it identifies that these methods enforce rules when changing object state, which is the essence of encapsulation and data protection. Choice B is incorrect because it contradicts the purpose of encapsulation - methods provide controlled access, not direct access to private fields. Students should practice writing validation logic in methods and understand why direct field access is dangerous. Create scenarios where uncontrolled access would break program logic to reinforce the importance of accessor and mutator methods.
Considering the Java class example below, which of the following best describes polymorphism as applied?
public class Animal {
public void speak() { System.out.println("..."); }
}
public class Dog extends Animal {
@Override
public void speak() { System.out.println("Woof"); }
}
public class Cat extends Animal {
@Override
public void speak() { System.out.println("Meow"); }
}
public class Demo {
public static void makeItSpeak(Animal a) {
a.speak(); // same call, different results
}
}
// Encapsulation: fields would be private with public methods.
// Inheritance: Dog/Cat extend Animal.
Based on the class structure presented above, which of the following best describes polymorphism as applied in the 'Dog' and 'Cat' classes?
Explanation: This question tests AP Computer Science A understanding of polymorphism and dynamic method binding in Java. Polymorphism enables a single method call to exhibit different behaviors based on the actual object type at runtime, even when accessed through a superclass reference - this is the essence of 'many forms' in object-oriented programming. In the example, the makeItSpeak() method accepts an Animal parameter, but when a.speak() is called, Java determines at runtime whether the object is actually a Dog or Cat, executing the appropriate overridden version of speak(). Choice A is correct because it accurately describes dynamic binding: the method call uses the object's actual class (Dog or Cat) at runtime, not the reference type (Animal). Choice D is incorrect because fields and methods exist in separate namespaces in Java - a field cannot override a method, and this statement demonstrates a fundamental misunderstanding of Java's structure. Students should trace through polymorphic method calls using debuggers to see runtime type determination in action.
Considering the Java class example below, what is the purpose of the constructor?
// Car represents a real-world car object.
public class Car {
// Fields describe state
private String make;
private String model;
private int year;
// Constructor
public Car(String make, String model, int year) {
this.make = make;
this.model = model;
this.year = year;
}
// Methods describe behavior
public void start() {
// start the car
}
public void stop() {
// stop the car
}
}
// Encapsulation keeps fields private and exposes behavior via methods.
// Inheritance and polymorphism allow subclasses to reuse and override methods.
Based on the class structure presented above, what is the purpose of the constructor in the Java class example?
Explanation: This question tests AP Computer Science A understanding of constructors and their role in object initialization within Java classes. Constructors are special methods that execute when an object is created using the 'new' keyword, setting up the initial state of the object by assigning values to its fields. In the Car class example, the constructor takes three parameters (make, model, year) and uses them to initialize the corresponding private fields, ensuring every Car object starts with meaningful data. Choice A is correct because it accurately describes the constructor's primary purpose of initializing the object's fields at the moment of creation. Choice C is incorrect because Java uses automatic garbage collection rather than explicit destructors, and constructors have nothing to do with object deletion. Students should practice writing constructors that validate input parameters and understand the difference between constructors and regular methods, noting that constructors have no return type and must match the class name.
A programmer is designing a class to represent a bank account. Which of the following best demonstrates proper encapsulation principles while maintaining necessary functionality for account management?
Explanation: Option B correctly implements encapsulation by making instance variables private (hiding internal state) while providing controlled access through public getter methods and validated setter methods. This allows the class to maintain control over how its data is accessed and modified. Option A violates encapsulation by making variables public. Option C uses protected access which is less secure than private. Option D is too restrictive as it prevents any modification, which would make the class impractical for a bank account that needs balance updates.
public class Student { private String name; private int grade; private static int studentCount = 0;
public Student(String n, int g) {
name = n;
grade = g;
studentCount++;
}
public static int getStudentCount() {
return studentCount;
}
public void updateGrade(int newGrade) {
grade = newGrade;
}
}
Based on the Student class shown above, what will happen if a programmer attempts to access the studentCount variable directly from outside the class using Student.studentCount?
Explanation: Option C is correct because studentCount is declared as private, which means it cannot be accessed directly from outside the class, regardless of whether it's static or not. The access modifier (private) takes precedence over the static keyword for access control. Option A is incorrect because private static variables are not accessible from outside the class. Option B is wrong because static variables can be accessed using the class name, but only if they have appropriate access modifiers. Option D is incorrect because static variables maintain their values and are not reset when accessed.
A class named Rectangle has instance variables length and width, both of type double. The class needs a constructor that can handle cases where negative values are passed as parameters. Which constructor implementation best follows defensive programming practices?
Explanation: Option D best follows defensive programming practices by explicitly checking for invalid input and throwing an appropriate exception when negative or zero values are provided. This makes the error condition clear and forces the calling code to handle invalid input properly. Option A provides no validation. Option B silently converts negative values to positive ones, which could mask programming errors. Option C checks for validity but leaves the instance variables uninitialized when invalid input is provided, creating an object in an undefined state.
Which of the following statements about method overloading in a class is most accurate regarding both compilation and runtime behavior?
Explanation: Option C is correct because method overloading is resolved at compile time based on the method signature (name and parameter list), not at runtime. The compiler determines which overloaded method to call based on the declared types of the arguments passed. Option A is incorrect because overloaded methods are distinguished by parameter lists, not return types, and they should have different parameter lists. Option B incorrectly states that method selection happens at runtime (that's method overriding, not overloading). Option D is incorrect because overloaded methods don't require the same return type or different access modifiers, and selection doesn't occur at runtime.
public class BankAccount { private String accountNumber; private double balance;
public BankAccount(String accNum) {
accountNumber = accNum;
balance = 0.0;
}
public void deposit(double amount) {
balance += amount;
}
public boolean withdraw(double amount) {
if (amount <= balance) {
balance -= amount;
return true;
}
return false;
}
public String getAccountInfo() {
return "Account: " + accountNumber + ", Balance: $" + balance;
}
}
Examining the BankAccount class above, which modification would best improve the class's robustness while maintaining its current functionality?
Explanation: Option B best improves robustness by adding input validation to prevent logical errors. Currently, the deposit method accepts negative amounts, which could decrease the balance inappropriately - this is a significant logical flaw that should be prevented. Option A adds convenience but doesn't improve robustness against errors. Option C suggests using int instead of double, but this would actually limit functionality by preventing fractional currency amounts (cents). Option D adds tracking functionality but doesn't address any existing robustness issues in the current code.
public class Circle { private double radius; private static final double PI = 3.14159;
public Circle(double r) {
radius = r;
}
public double getArea() {
return PI * radius * radius;
}
public static double getCircumference(double r) {
return 2 * PI * r;
}
public void scale(double factor) {
radius *= factor;
}
}
Based on the Circle class above, which of the following method calls will result in a compilation error?
Explanation: Option D will cause a compilation error because getArea() is an instance method that requires an object instance to be called, but it's being called statically using the class name Circle.getArea(). Instance methods cannot be called without an object instance. Option A correctly calls an instance method on an object. Option B correctly calls a static method using the class name. Option C shows that static methods can be called on object instances (though not conventional, it's legal in Java).
public class Counter { private int value; private static int totalCounters;
public Counter() {
value = 0;
totalCounters++;
}
public Counter(int initialValue) {
value = initialValue;
totalCounters++;
}
public void increment() {
value++;
}
public int getValue() {
return value;
}
public static int getTotalCounters() {
return totalCounters;
}
}
Given the Counter class above, after executing the following code sequence, what will be the output of the final println statement?
Counter c1 = new Counter(); Counter c2 = new Counter(5); c1.increment(); c1.increment(); System.out.println(c1.getValue() + " " + Counter.getTotalCounters());
Explanation: Option A is correct. The code creates two Counter objects (c1 and c2), so totalCounters becomes 2. Object c1 starts with value 0 (default constructor) and is incremented twice, making its value 2. The getValue() method returns c1's value (2), and getTotalCounters() returns the static variable totalCounters (2). Option B incorrectly shows totalCounters as 1. Option C incorrectly adds c1's value to c2's initial value. Option D shows c1's value as 1, missing one increment operation.