Object-Oriented PHP
How PHP builds objects: typed, readonly and hooked properties, single inheritance plus interfaces and traits, late static binding and enums. Interviewers probe what the 8.x releases changed.
part ofPHPoverview, primer and where to startread it →on this pageshowhide
explore
- Instances & Cloning6 questions
- Constructors & Promotion5 questions
- Typed & Readonly Properties5 questions
- Inheritance & Overriding5 questions
- Interfaces & Contracts5 questions
- Traits5 questions
- Static Members & Late Binding5 questions
- Magic Methods6 questions
- Enumerations5 questions
questions
page 2 of 2In PHP 8.3 and later, what do typed class constants add, and when does static::NAME instead of self::NAME matter?
basics
~20 sSince PHP 8.3 a class constant can declare a type, and a subclass override must keep a compatible type. self::NAME reads the constant of the class the code is in; static::NAME reads the called class's value, so a subclass override takes effect.
In PHP, when a subclass does not redeclare a parent's static property, do the parent and subclass share one value, and why does that matter?
basics
~20 sYes. An inherited static property that the subclass does not redeclare is the same storage as the parent's, so writes through Child::$x change Parent::$x too. Redeclare it in the subclass, or key an array by static::class, to get per-class values.
In PHP, what rules govern a trait's abstract methods, static members, properties and constants once the trait is used by several classes?
basics
~20 sAbstract trait methods are requirements the host must implement compatibly. Static state exists once per using class, not per trait. A host may redeclare a trait property or constant only identically, and trait constants (8.2) and static members are used through the using class.
In PHP, how do insteadof and as resolve two traits that define the same method, and what else can the as operator change?
basics
~20 sTwo traits defining the same concrete method make PHP fail until insteadof picks one. The as operator adds an alias so the excluded body stays callable, and can also change visibility or, since 8.3, make the method final.
In PHP, when exactly does __destruct run, and why is it risky to rely on a destructor to flush or commit work?
basics
~20 s__destruct runs as soon as the last handle to an object disappears, or at shutdown if the object is still alive. Fatal errors skip it, cycles delay it and shutdown order is undefined, so commit work explicitly.
A PHP app stores order statuses as a string-backed enum in the database; what breaks when you rename a case, change a value or add a case?
basics
~20 sThe stored ->value is the contract. Renaming a case breaks code and anything that stored the name; changing a value makes from() throw ValueError on old rows; adding a case makes every default-less match throw UnhandledMatchError until handled.
In PHP 8.5, how does clone() with its $withProperties argument work, and why does it suit wither methods on readonly classes?
basics
~10 sSince PHP 8.5, clone($obj, ['prop' => $value]) shallow-copies the object, runs __clone(), then assigns the listed properties on the copy, even readonly ones, respecting visibility and set hooks. Withers become one line.
In PHP 8.4 and later, when would you declare a property on an interface instead of a getter method, and what can implementing classes satisfy it with?
basics
~20 sSince PHP 8.4 an interface can require a public readable, writable or read-write property with { get; }, { set; } or both. Implementers may use a plain public property, a hooked or virtual property, or, for get-only, a readonly one.
A PHP settings class exposes config keys as properties through __get; what does that hide from IDEs and static analysers, and how would you redesign it?
basics
~20 sMagic __get hides every property name and type from tools, so typos, renames and wrong types surface only at runtime. For known keys use typed readonly properties or 8.4 property hooks; if magic stays, document it with @property-read tags.
In PHP 8.4, how do property hooks and virtual properties work, and why can't a readonly class expose a computed passengerName hook?
basics
~20 sSince PHP 8.4, get and set hooks attach logic to a property. A property whose hooks never touch its own storage is virtual and takes no memory. Hooked properties cannot be readonly, so readonly classes cannot declare hooks.
In a PHP model base class, how do you write a static factory such as User::create() that returns the subclass, and what can break it?
basics
~20 sWrite create() as return new static(...) with a : static return type, so User::create() builds a User. Guard the constructor signature (final, abstract or interface-declared), because a subclass constructor with different parameters makes new static throw.
In a PHP CMS where Article, Page and MediaFile need timestamps and soft deletes, when is a trait the right tool, and how do you stop it becoming hidden coupling?
basics
~20 sA trait fits small, cohesive behaviour that several unrelated classes need verbatim, such as timestamp and soft-delete fields. Keep it honest by pairing it with an interface, declaring its needs as abstract methods, and leaving real dependencies to injected services.
In PHP, what is an anonymous class created with new class, and when is it a better fit than a named class?
basics
~20 sAn anonymous class is declared and instantiated in one new class expression; it can take constructor arguments, extend, implement and use traits. It suits one-off implementations such as test doubles or small adapters, not reusable types.
In PHP 8, what is the Stringable interface, when does a class implement it without declaring it, and why type a parameter as string|Stringable?
basics
~20 sStringable, added in PHP 8.0, is the interface of objects with __toString(). A class that declares __toString() implements it automatically. Typing string|Stringable accepts strings and such objects even under strict_types, where a plain string type rejects objects.
In PHP, what do the __debugInfo and __set_state magic methods customise, and which built-in functions call them?
basics
~20 s__debugInfo returns the array var_dump and print_r show for an object, for example to hide a secret. __set_state is a static factory that var_export's output calls when that code is evaluated, rebuilding the object from an array of properties.
In PHP 8, which rules does the engine enforce when a class declares magic methods such as __get, __call or __toString?
basics
~20 sMagic methods have fixed parameter counts, no by-reference parameters, and only __callStatic and __set_state may be static. Since PHP 8.0, declared types must also match the documented signatures. A non-public magic method just triggers a warning.
After upgrading to PHP 8.1 or later, a class extending ArrayObject logs "Return type of Bag::count() should either be compatible"; what does it mean and how do you fix it?
basics
~10 sSince PHP 8.1 most non-final internal methods carry tentative return types; an override without a compatible one raises E_DEPRECATED. Declaring the type fixes it; #[\ReturnTypeWillChange] only suppresses the notice until checking becomes strict.
showing 31–47 of 47