单例模式:单例模式确保一个类只能在全局中实例化一次,这在需要限制特定类只能创建一个对象时非常有用,比如数据库连接、日志记录器等。
class Singleton {
private static $instance;
private function __construct() { }
public static function getInstance() {
if (null === self::$instance) {
self::$instance = new self();
}
return self::$instance;
}
}
-
private static $instance
:这是保存类的唯一实例的静态私有变量。它用于存储单例实例。 -
private function __construct()
:这是私有的构造函数,防止外部代码通过new
操作符创建类的新实例。这是单例模式的关键,因为它确保类只能有一个实例。 -
public static function getInstance()
:这是获取单例实例的静态方法。如果当前没有实例存在,它会创建一个新的实例并将其存储在$instance
变量中,然后返回该实例。如果已经有一个实例存在,它将直接返回该实例。
这样,无论在代码中调用多少次 Singleton::getInstance()
,都将返回相同的单一实例,确保了全局只有一个类的实例存在
工厂模式:工厂模式用于创建对象,但不直接使用 new
操作符。它通常包括一个工厂类,负责根据参数或条件创建不同类型的对象,laravel的从容器中实例化对象就是工厂模式体现,按需生产实例。
interface Vehicle {
public function drive();
}
class Car implements Vehicle {
public function drive() {
echo "Driving a car.";
}
}
class Bike implements Vehicle {
public function drive() {
echo "Riding a bike.";
}
}
class VehicleFactory {
public static function create($type) {
if ($type === 'car') {
return new Car();
} elseif ($type === 'bike') {
return new Bike();
}
return null;
}
}
使用工厂模式可以不用关心对象是如何生产的,他统一封装在一个独立的工厂类中,通过直接对抽象类和实现类绑定来解耦代码,有高度的复用性。
观察者模式(Observer Pattern): 观察者模式定义了一种对象间的一对多依赖关系,当一个对象的状态发生改变时,它的所有依赖者都会得到通知并自动更新。
interface Observer {
public function update($data);
}
class ConcreteObserver implements Observer {
public function update($data) {
echo "Received data: $data";
}
}
class Subject {
private $observers = [];
public function attach(Observer $observer) {
$this->observers[] = $observer;
}
public function notify($data) {
foreach ($this->observers as $observer) {
$observer->update($data);
}
}
}
上述代码实现一个Observer抽象类,通过ConcreteObserver 实现这个抽象类,并且实现了一个update方法来处理更新,subject类调用attach方法将所有要通知的对象写入observers的私有属性中,然后用notify方法通知。
// 创建观察者和主题对象
$observer1 = new ConcreteObserver();
$observer2 = new ConcreteObserver();
$subject = new Subject();
// 将观察者对象附加到主题
$subject->attach($observer1);
$subject->attach($observer2);
// 通知观察者有关状态变化
$subject->notify("New data is available.");
// 输出:
// Received data: New data is available.
// Received data: New data is available.
具体的应用场景和好处:
发布订阅,可重复性以及代码的松偶,应用场景图形界面监听一些组件然后通知,事件处理,以及处理顺序通过订阅观察者类来接收通知,分布式系统中的发布服务和订阅服务。
策略模式(Strategy Pattern): 策略模式定义了一系列算法,将它们封装成独立的策略对象,使得这些算法可以互相替换,而不影响客户端代码。
interface PaymentStrategy {
public function pay($amount);
}
class CreditCardPayment implements PaymentStrategy {
public function pay($amount) {
echo "Paid $amount using credit card.";
}
}
class PayPalPayment implements PaymentStrategy {
public function pay($amount) {
echo "Paid $amount using PayPal.";
}
}
通过定义创建了一个PaymentStrategy的抽象方法,有两个继承来处理。
当需要CreditCardPayment实现类
$creditCardPayment = new CreditCardPayment();
$paymentAmount = 100.00;
$creditCardPayment->pay($paymentAmount);
当需要PaymentStrategy实现类
$payPalPayment = new PayPalPayment();
$paymentAmount = 100.00;
$payPalPayment->pay($paymentAmount);
策略模式的好处在于它允许在运行时动态地选择和切换不同的支付策略,而不需要修改客户端代码。这使得代码更具灵活性和可扩展性。例如,你可以轻松地根据用户的选择或其他条件切换支付策略。
策略模式还有助于避免代码重复,因为支付逻辑被封装在独立的策略类中,可以在不同部分的应用程序中共享和重用。