什么是PHP中的工厂设计模式?

Jas*_*vis 84 php factories

这让我感到困惑,用最简单的术语来说它是做什么的?假装你正在向你的母亲或其他人解释.

Tyl*_*ter 170

工厂创建一个对象.所以,如果你想建立

 class A{
    public $classb;
    public $classc;
    public function __construct($classb, $classc)
    {
         $this->classb = $classb;
         $this->classc = $classc;
    }
  }
Run Code Online (Sandbox Code Playgroud)

每次创建对象时,您都不希望依赖于必须执行以下代码

$obj = new ClassA(new ClassB, new Class C);
Run Code Online (Sandbox Code Playgroud)

这就是工厂的用武之地.我们为我们定义了一个工厂来处理这个问题:

class Factory{
    public function build()
    {
        $classc = $this->buildC();
        $classb = $this->buildB();
        return $this->buildA($classb, $classc);

    }

    public function buildA($classb, $classc)
    {
        return new ClassA($classb, $classc);
    }

    public function buildB()
    {
        return new ClassB;
    }

    public function buildC()
    {
        return new ClassC;
    }
}
Run Code Online (Sandbox Code Playgroud)

现在我们所要做的就是

$factory = new Factory;
$obj     = $factory->build();
Run Code Online (Sandbox Code Playgroud)

真正的优势是你想要改变班级.让我们说我们想传递一个不同的ClassC:

class Factory_New extends Factory{
    public function buildC(){
        return new ClassD;
    }
}
Run Code Online (Sandbox Code Playgroud)

或新的ClassB:

class Factory_New2 extends Factory{
    public function buildB(){
        return new ClassE;
    }
}
Run Code Online (Sandbox Code Playgroud)

现在我们可以使用继承来轻松修改类的创建方式,以便放入一组不同的类.

一个很好的例子可能是这个用户类:

class User{
    public $data;
    public function __construct($data)
    {
        $this->data = $data;
    }
}
Run Code Online (Sandbox Code Playgroud)

在这个类中$data是我们用来存储数据的类.现在,对于这个类,我们假设我们使用Session来存储我们的数据.工厂看起来像这样:

class Factory{
    public function build()
    {
        $data = $this->buildData();
        return $this->buildUser($data);
    }

    public function buildData()
    {
        return SessionObject();
    }

    public function buildUser($data)
    {
        return User($data);
    }
}
Run Code Online (Sandbox Code Playgroud)

现在,让我们说我们想要将所有数据存储在数据库中,更改它非常简单:

class Factory_New extends Factory{
    public function buildData()
    {
        return DatabaseObject();
    }
}
Run Code Online (Sandbox Code Playgroud)

工厂是我们用来控制将对象放在一起的设计模式,使用正确的工厂模式可以让我们创建我们需要的自定义对象.

  • 这是很多打字.现在我必须在某个时候把它放在我的维基上. (3认同)
  • 友善且乐于助人。向你致敬,伙计。 (2认同)

ale*_*lex 18

就像一个真实的工厂,它创造了一些东西并将其归还.

想象一下这样的事情

$joe = new Joe();
$joe->say('hello');
Run Code Online (Sandbox Code Playgroud)

或工厂方法

Joe::Factory()->say('hello');
Run Code Online (Sandbox Code Playgroud)

工厂方法的实现将创建一个新实例并将其返回.


Sha*_*are 7

当您处理多种资源并想要实现高级抽象时,工厂设计模式非常好。

让我们将其分为不同的部分。

假设您必须实现抽象,并且类的用户不需要关心在类定义中实现的内容。

他/她只需要担心您的类方法的使用。

例如,您的项目有两个数据库

class MySQLConn {

        public function __construct() {
                echo "MySQL Database Connection" . PHP_EOL;
        }

        public function select() {
                echo "Your mysql select query execute here" . PHP_EOL;
        }

}

class OracleConn {

        public function __construct() {
                echo "Oracle Database Connection" . PHP_EOL;
        }

        public function select() {
                echo "Your oracle select query execute here" . PHP_EOL;
        }

}
Run Code Online (Sandbox Code Playgroud)

您的Factory类将负责创建数据库连接对象。

class DBFactory {

        public static function getConn($dbtype) {

                switch($dbtype) {
                        case "MySQL":
                                $dbobj = new MySQLConn();
                                break;
                        case "Oracle":
                                $dbobj = new OracleConn();
                                break;
                        default:
                                $dbobj = new MySQLConn();
                                break;
                }

                return $dbobj;
        }

}
Run Code Online (Sandbox Code Playgroud)

用户只需要传递数据库类型的名称

$dbconn1 = DBFactory::getConn("MySQL");
$dbconn1->select();
Run Code Online (Sandbox Code Playgroud)

输出:

MySQL Database Connection
Your mysql select query execute here
Run Code Online (Sandbox Code Playgroud)

将来您可能拥有不同的数据库,那么您无需更改整个代码,只需传递新的数据库类型,其他代码将在不进行任何更改的情况下运行。

$dbconn2 = DBFactory::getConn("Oracle");
$dbconn2->select();
Run Code Online (Sandbox Code Playgroud)

输出:

Oracle Database Connection
Your oracle select query execute here
Run Code Online (Sandbox Code Playgroud)

希望这会有所帮助。