B3.2 Fundamentals of OOP for multiple classes questions for IB Computer Science

115 questions on Fundamentals of OOP for multiple classes, written by Augment in the style of IB exam papers. Six of them are below in full, to answer on paper.

  • IB Computer Science
  • Part of B3 Object-oriented programming
  • HL only

Questions by paper and level

PaperQuestions
Paper 2115

Counted on

Questions to try

Written by Augment in the style of IB exams, not past papers. Answer them on paper, then check each one against its markscheme with a free account.

Question 1 · CS-01324Paper 2 · 6 marks

A school library lends books and DVDs. Every item is stored as an object of one of the classes below.

Python

Python
class LibraryItem:
    def __init__(self, title):
        self.title = title

    def loan_days(self):
        return 21

    def label(self):
        return self.title + " (" + str(self.loan_days()) + " days)"


class Book(LibraryItem):
    def __init__(self, title, author):
        super().__init__(title)
        self.author = author


class DVD(LibraryItem):
    def loan_days(self):
        return 7

Java

Java
public class LibraryItem {
    protected String title;

    public LibraryItem(String title) {
        this.title = title;
    }

    public int loanDays() {
        return 21;
    }

    public String label() {
        return title + " (" + loanDays() + " days)";
    }
}

public class Book extends LibraryItem {
    private String author;

    public Book(String title, String author) {
        super(title);
        this.author = author;
    }
}

public class DVD extends LibraryItem {
    public DVD(String title) {
        super(title);
    }

    @Override
    public int loanDays() {
        return 7;
    }
}
  1. (a)

    State the name of the class that DVD inherits from.

    1 mark

  2. (b)

    Identify two members (attributes or methods) that a Book object has but that are not declared in the Book class.

    2 marks

  3. (c)

    The following code is run.

    Python

    Python
    items = [Book("Dune", "Herbert"), DVD("Up"), LibraryItem("Atlas")]
    for item in items:
        print(item.label())

    Java

    Java
    ArrayList<LibraryItem> items = new ArrayList<LibraryItem>();
    items.add(new Book("Dune", "Herbert"));
    items.add(new DVD("Up"));
    items.add(new LibraryItem("Atlas"));
    for (LibraryItem item : items) {
        System.out.println(item.label());
    }

    State the output.

    3 marks

Question 2 · CS-01325Paper 2 · 16 marks

A ride-share company models its journeys with the classes in Figure 1. In the UML, - means private, + public and # protected. (In Python, private attributes are written with two leading underscores and protected ones with one.)

UML class diagram. Ride: private rideId String, private distanceKm double, protected baseFare double; public Ride(rideId, distanceKm), getDistanceKm(): double, fare(): double. PoolRide (passengers int) and LuxuryRide (surcharge double) inherit from Ride; each has a constructor and fare(): double.
Figure 1

The constructor of Ride sets baseFare to 3.0. The method fare() in Ride returns baseFare + 2.0 * distanceKm. In PoolRide, fare() returns the normal Ride fare divided by the number of passengers.

  1. (a)

    State the name of the superclass in Figure 1.

    1 mark

  2. (b)

    Outline what the # symbol before baseFare means for the classes in Figure 1.

    2 marks

  3. (c)

    Identify two members that LuxuryRide inherits from Ride.

    2 marks

  4. (d)

    In LuxuryRide, fare() returns the normal Ride fare plus the surcharge.

    Construct, in Python or Java, the LuxuryRide class.

    5 marks

  5. (e)

    The following code is run.

    Python

    Python
    rides = [Ride("R1", 10), PoolRide("R2", 10, 2), LuxuryRide("R3", 10, 8.0)]
    total = 0
    for r in rides:
        print(r.fare())
        total = total + r.fare()
    print(total)

    Java

    Java
    ArrayList<Ride> rides = new ArrayList<Ride>();
    rides.add(new Ride("R1", 10));
    rides.add(new PoolRide("R2", 10, 2));
    rides.add(new LuxuryRide("R3", 10, 8.0));
    double total = 0;
    for (Ride r : rides) {
        System.out.println(r.fare());
        total = total + r.fare();
    }
    System.out.println(total);

    State the output.

    3 marks

  6. (f)

    Explain how polymorphism allows the loop in part (e) to calculate the correct total without checking the type of each ride.

    3 marks

Question 3 · CS-01326Paper 2 · 7 marks

A hospital's staff system has a class Employee and a subclass Nurse. A nurse is paid one twelfth of the yearly salary each month, plus 50 for each night shift.

Python

Python
class Employee:
    def __init__(self, name, salary):
        self._name = name
        self.__salary = salary

    def get_salary(self):
        return self.__salary


class Nurse(Employee):
    def __init__(self, name, salary, night_shifts):
        super().__init__(name, salary)
        self.__night_shifts = night_shifts

    def monthly_pay(self):
        return self.__salary / 12 + 50 * self.__night_shifts

Java

Java
public class Employee {
    protected String name;
    private double salary;

    public Employee(String name, double salary) {
        this.name = name;
        this.salary = salary;
    }

    public double getSalary() {
        return salary;
    }
}

public class Nurse extends Employee {
    private int nightShifts;

    public Nurse(String name, double salary, int nightShifts) {
        super(name, salary);
        this.nightShifts = nightShifts;
    }

    public double monthlyPay() {
        return salary / 12 + 50 * nightShifts;
    }
}

When the programmer tries to work out a nurse's monthly pay, the method monthly_pay / monthlyPay fails.

  1. (a)

    Explain why monthly_pay / monthlyPay fails.

    3 marks

  2. (b)

    Construct a corrected version of monthly_pay / monthlyPay that does not change the Employee class.

    2 marks

  3. (c)

    Outline one reason why the hospital might keep salary private rather than making it protected.

    2 marks

Question 4 · CS-01327Paper 2 · 8 marks

A game studio is writing a fantasy game. Every character in the game is an object of the class Character or of one of its subclasses.

Python

Python
class Character:
    def __init__(self, name, health, power):
        self._name = name
        self._health = health
        self._power = power

    def attack(self):
        return self._power

    def take_damage(self, amount):
        self._health = self._health - amount

Java

Java
public class Character {
    protected String name;
    protected int health;
    protected int power;

    public Character(String name, int health, int power) {
        this.name = name;
        this.health = health;
        this.power = power;
    }

    public int attack() {
        return power;
    }

    public void takeDamage(int amount) {
        health = health - amount;
    }
}
  1. (a)

    A Wizard is a Character that also has an integer mana, set by its constructor. When a wizard attacks, if its mana is at least 10, it uses 10 mana and returns double the normal attack value; otherwise it returns the normal attack value.

    For example, a wizard created with power 15 and mana 25 returns 30, then 30, then 15 from three calls to attack().

    Construct, in Python or Java, the Wizard class.

    6 marks

  2. (b)

    Outline one benefit of Wizard inheriting from Character rather than being written as a separate class.

    2 marks

Question 5 · CS-01328Paper 2 · 14 marks

A weather station records readings from several kinds of sensor. All sensors share the class Sensor, and each kind of sensor is a subclass.

Python

Python
class Sensor:
    def __init__(self, sensor_id):
        self._sensor_id = sensor_id
        self._readings = []

    def add_reading(self, value):
        self._readings.append(value)

    def latest(self):
        return self._readings[len(self._readings) - 1]

    def units(self):
        return ""

    def report(self):
        return self._sensor_id + ": " + str(self.latest()) + self.units()


class TemperatureSensor(Sensor):
    def units(self):
        return " C"

    def is_alert(self):
        return self.latest() > 35


class RainGauge(Sensor):
    def units(self):
        return " mm"

    def add_reading(self, value):
        if value >= 0:
            super().add_reading(value)

Java

Java
public class Sensor {
    protected String sensorId;
    protected ArrayList<Integer> readings = new ArrayList<Integer>();

    public Sensor(String sensorId) {
        this.sensorId = sensorId;
    }

    public void addReading(int value) {
        readings.add(value);
    }

    public int latest() {
        return readings.get(readings.size() - 1);
    }

    public String units() {
        return "";
    }

    public String report() {
        return sensorId + ": " + latest() + units();
    }
}

public class TemperatureSensor extends Sensor {
    public TemperatureSensor(String sensorId) {
        super(sensorId);
    }

    @Override
    public String units() {
        return " C";
    }

    public boolean isAlert() {
        return latest() > 35;
    }
}

public class RainGauge extends Sensor {
    public RainGauge(String sensorId) {
        super(sensorId);
    }

    @Override
    public String units() {
        return " mm";
    }

    @Override
    public void addReading(int value) {
        if (value >= 0) {
            super.addReading(value);
        }
    }
}
  1. (a)

    Identify the method that is overridden in both subclasses.

    1 mark

  2. (b)

    The following code is run.

    Python

    Python
    t = TemperatureSensor("T1")
    r = RainGauge("R1")
    t.add_reading(31)
    t.add_reading(36)
    r.add_reading(4)
    r.add_reading(-2)
    sensors = [t, r]
    for s in sensors:
        print(s.report())
    print(t.is_alert())

    Java

    Java
    TemperatureSensor t = new TemperatureSensor("T1");
    RainGauge r = new RainGauge("R1");
    t.addReading(31);
    t.addReading(36);
    r.addReading(4);
    r.addReading(-2);
    Sensor[] sensors = {t, r};
    for (Sensor s : sensors) {
        System.out.println(s.report());
    }
    System.out.println(t.isAlert());

    State the output.

    3 marks

  3. (c)

    The method report() is written only once, in Sensor, yet it gives different units for each kind of sensor.

    Explain how this happens.

    3 marks

  4. (d)

    The station adds a wind sensor. A WindSensor reports in " km/h" and has an extra method gust() that returns the highest reading recorded. You may assume at least one reading has been added. You must not use built-in functions such as max() (Python) or Collections.max (Java).

    Construct, in Python or Java, the WindSensor class.

    5 marks

  5. (e)

    Outline one advantage of RainGauge calling the parent's add_reading / addReading method rather than repeating the code that adds a value to the list.

    2 marks

Question 6 · CS-01329Paper 2 · 9 marks

A bank allows at most three withdrawals from a savings account. The class SavingsAccount extends the general class Account.

Python

Python
class Account:
    def __init__(self, balance):
        self._balance = balance

    def withdraw(self, amount):
        if amount <= self._balance:
            self._balance = self._balance - amount
            return True
        return False


class SavingsAccount(Account):
    def __init__(self, balance):
        super().__init__(balance)
        self.__withdrawals = 0

    def withdraw(self, amount):
        if self.__withdrawals < 3 and super().withdraw(amount):
            self.__withdrawals = self.__withdrawals + 1
            return True
        return False

Java

Java
public class Account {
    protected int balance;

    public Account(int balance) {
        this.balance = balance;
    }

    public boolean withdraw(int amount) {
        if (amount <= balance) {
            balance = balance - amount;
            return true;
        }
        return false;
    }
}

public class SavingsAccount extends Account {
    private int withdrawals;

    public SavingsAccount(int balance) {
        super(balance);
        withdrawals = 0;
    }

    @Override
    public boolean withdraw(int amount) {
        if (withdrawals < 3 && super.withdraw(amount)) {
            withdrawals = withdrawals + 1;
            return true;
        }
        return false;
    }
}

A savings account is opened with a balance of 100, and then withdraw is called with these amounts, in order: 30, 80, 20, 10, 5.

  1. (a)

    Copy and complete the trace table below.

    Call

    amount

    Value returned

    balance after the call

    withdrawals after the call

    1

    30

    2

    80

    3

    20

    4

    10

    5

    5

    4 marks

  2. (b)

    Outline why SavingsAccount calls the parent's withdraw method instead of repeating its code.

    2 marks

  3. (c)

    A programmer swaps the two conditions in the if statement of the overriding method so that the parent's withdraw is called first.

    Explain how this change would affect the account in the sequence of calls above.

    3 marks

Practice all 115 in Augment

Free with an account. Every question has its markscheme, and Augment keeps the ones you got wrong so you can come back to them.

The notes on B3.2 Fundamentals of OOP for multiple classes

More questions in Object-oriented programming

  1. B3.1Fundamentals of OOP for a single class
  2. B3.2Fundamentals of OOP for multiple classesThis page

Check your answers in Augment

A free account opens all 115 questions on Fundamentals of OOP for multiple classes with their markschemes, and keeps a record of what you have marked.