Inheritance in PHP

Parent Class: Car

The parent class is a plain old PHP class. It has two state variables: licensePlateNumber and licensePlateState.

<?php
/**
 * Small Cross Section of a Car
 *
 * This Car is meant to illustrate inheritance and how it can be employed to facilitate code reuse. In this simple
 * world, a "Car" is anything that one can legally attach a license plate to and circulate on public roads.
 *
 * @author Dylan McDonald <dmcdonald21@cnm.edu>
 **/
class Car {
	/**
	 * license plate number for this Car
	 * @var string $licensePlateNumber
	 **/
	protected $licensePlateNumber;
	/**
	 * license plate state for this Car
	 * @var string $licensePlateState
	 **/
	protected $licensePlateState;


	/**
	 * constructor for this Car
	 *
	 * @param string $newLicensePlateNumber license plate number of this Car
	 * @param string $newLicensePlateState state license of this Car
	 * @throws InvalidArgumentException if data types are not valid
	 * @throws LengthException if strings are too large
	 * @throws UnexpectedValueException when values are misformatted
	 * @throws Exception if some other exception is thrown
	 **/
	public function __construct($newLicensePlateNumber, $newLicensePlateState) {
		try {
			$this->setLicensePlateNumber($newLicensePlateNumber);
			$this->setLicensePlateState($newLicensePlateState);
		} catch(InvalidArgumentException $invalidArgument) {
			throw(new InvalidArgumentException($invalidArgument->getMessage(), 0, $invalidArgument));
		} catch(LengthException $length) {
			throw(new LengthException($length->getMessage(), 0, $length));
		} catch(UnexpectedValueException $unexpectedValue) {
			throw(new UnexpectedValueException($unexpectedValue->getMessage(), 0, $unexpectedValue));
		} catch(Exception $exception) {
			throw(new Exception($exception->getMessage(), 0, $exception));
		}
	}


	/**
	 * accessor method for license plate number
	 *
	 * @return string value of license plate number
	 **/
	public function getLicensePlateNumber() {
		return($this->licensePlateNumber);
	}

	/**
	 * mutator method for license plate number
	 *
	 * @param string $newLicensePlateNumber new value of license plate number
	 * @throws InvalidArgumentException if $newLicensePlateNumber is empty or insecure
	 * @throws LengthException if $newLicensePlateNumber > 10 characters
	 **/
	public function setLicensePlateNumber($newLicensePlateNumber) {
		// verify the license plate number is secure
		$newLicensePlateNumber = trim($newLicensePlateNumber);
		$newLicensePlateNumber = filter_var($newLicensePlateNumber, FILTER_SANITIZE_STRING);
		if(empty($newLicensePlateNumber) === true) {
			throw(new InvalidArgumentException("license plate number empty or insecure"));
		}

		// verify the license plate number will fit in the database
		if(strlen($newLicensePlateNumber) > 10) {
			throw(new LengthException("license plate number too large"));
		}

		// store the license plate number
		$this->licensePlateNumber = $newLicensePlateNumber;
	}

	/**
	 * accessor method for license plate state
	 *
	 * @return string value of license plate state
	 **/
	public function getLicensePlateState() {
		return($this->licensePlateState);
	}

	/**
	 * mutator method for license plate state
	 *
	 * @param string $newLicensePlateState new value of license plate state
	 * @throws InvalidArgumentException if $newLicensePlateState is empty or insecure
	 * @throws UnexpectedValueException if $newLicensePlateState is not correctly formatted
	 **/
	public function setLicensePlateState($newLicensePlateState) {
		// verify the license plate state is secure
		$newLicensePlateState = trim($newLicensePlateState);
		$newLicensePlateState = filter_var($newLicensePlateState, FILTER_SANITIZE_STRING);
		if(empty($newLicensePlateState) === true) {
			throw(new InvalidArgumentException("license plate state empty or insecure"));
		}

		// verify the license plate state will fit in the database
		if(preg_match("/^[A-Z]{2}$/", $newLicensePlateState) !== 1) {
			throw(new UnexpectedValueException("license plate state incorrectly formatted"));
		}
	}
}

Child Class: HybridCar

The child class has access to all aspects of the parent class. Notice the constructor makes use of the parent keyword to fully take advantage of the parent's logic before setting it's own variable, batteryCapacity.

<?php
// grab the parent class
require_once("car.php");

/**
 * Small Cross Section of a HybridCar
 *
 * This HybridCar is meant to illustrate inheritance and how it can be employed to facilitate code reuse. In this simple
 * world, a "HybridCar" is anything that has a battery as a power source and circulate on public roads.
 *
 * @author Dylan McDonald <dmcdonald21@cnm.edu>
 **/
class HybridCar extends Car {
	/**
	 * capacity of the battery of this HybridCar in Ampere-hours (Ah)
	 * @var float $batteryCapacity
	 **/
	protected $batteryCapacity;

	/**
	 * constructor for this HybridCar
	 *
	 * @param string $newLicensePlateNumber license plate number of this Car
	 * @param string $newLicensePlateState state license of this Car
	 * @throws InvalidArgumentException if data types are not valid
	 * @throws LengthException if strings are too large
	 * @throws UnexpectedValueException when values are misformatted
	 * @throws Exception if some other exception is thrown
	 **/
	public function __construct($newLicensePlateNumber, $newLicensePlateState, $newBatteryCapacity) {
		try {
			// first, call the Car constructor
			parent::__construct($newLicensePlateNumber, $newLicensePlateState);
			// then, set the HybridCar's unique variable
			$this->setBatteryCapacity($newBatteryCapacity);
		} catch(InvalidArgumentException $invalidArgument) {
			throw(new InvalidArgumentException($invalidArgument->getMessage(), 0, $invalidArgument));
		} catch(LengthException $length) {
			throw(new LengthException($length->getMessage(), 0, $length));
		} catch(RangeException $range) {
			throw(new RangeException($range->getMessage(), 0, $range));
		} catch(UnexpectedValueException $unexpectedValue) {
			throw(new UnexpectedValueException($unexpectedValue->getMessage(), 0, $unexpectedValue));
		} catch(Exception $exception) {
			throw(new Exception($exception->getMessage(), 0, $exception));
		}

	}

	/**
	 * accessor method for battery capacity
	 *
	 * @return float value of battery capacity
	 **/
	public function getBatteryCapacity() {
		return($this->batteryCapacity);
	}

	/**
	 * mutator method for battery capacity
	 *
	 * @param float $newBatteryCapacity new value of battery capacity
	 * @throws InvalidArgumentException if $newBatteryCapacity is not a double
	 * @throws RangeException if $newBatteryCapacity is negative
	 **/
	public function setBatteryCapacity($newBatteryCapacity) {
		// verify the battery capacity is valid
		$newBatteryCapacity = filter_var($newBatteryCapacity, FILTER_VALIDATE_FLOAT);
		if($newBatteryCapacity === false) {
			throw(new InvalidArgumentException("battery capacity is not a valid double"));
		}

		// verify the battery capacity is positive
		if($newBatteryCapacity < 0.0) {
			throw(new RangeException("battery capacity is not positive"));
		}

		// store the battery capacity
		$this->batteryCapacity = floatval($newBatteryCapacity);
	}
}