php设计模式之生成器模式详解

生成器模式

生成器模式是一种创建型设计模式, 使你能够分步骤创建复杂对象。 该模式允许你使用相同的创建代码生成不同类型和形式的对象。

  1. 该模式会将对象构造过程划分为一组步骤,但是不是所有步骤都需要调用
  2. 最常用的一些例子就是sql查询的查询构造器
  3. 当有不同的查询的时候,只需要调用不同的步骤即可
  4. 再比如,sql查询中,mysql的limit,offset 写法和 postgreSql不一样,别的都一样,这个时候就只需要改写一个方法即可

代码示例

  • 数据查询接口
interface QueryBuilder
{
    public function reset():void;
    public function select(array $fields = ["*"]):self;

    public function table(string $table):self;

    public function where(string $field, $value, $operator = '='):self;

    public function limit($start, $offset):self;

    public function getSql(): string;
}
  • mysql 查询构造器
class MysqlQueryBuilder implements QueryBuilder
{
    /**
     * @var stdClass|null
     */
    protected ?stdClass $query = null;

    #[Pure]
    public function __construct()
    {
        $this->query = new \stdClass();
    }


    public function select(array $fields = ["*"]): QueryBuilder
    {
        // TODO: Implement select() method.
        if (empty($this->query)) {
            $this->reset();
        }

        $this->query->field = '';

        foreach ($fields as $item) {
            $this->query->field .= "`" . $item . "`,";
        }
        $this->query->field = rtrim($this->query->field, ',');

        $this->query->type = 'select';

        return $this;
    }

    public function table(string $table): QueryBuilder
    {
        // TODO: Implement table() method.
        $this->reset();

        $this->query->table = "`" . $table . "`";

        return $this;
    }

    /**
     * @throws Exception
     */
    public function where(string $field, $value, $operator = '='): QueryBuilder
    {
        if (empty($this->query)) {
            $this->reset();
        }
        // TODO: Implement where() method.
        if (!in_array($this->query->type, ['select', 'update', 'delete'])) {
            throw new \Exception("WHERE can only be added to SELECT, UPDATE OR DELETE");
        }

        $this->query->where[] = "`$field` $operator '$value'";

        return $this;
    }

    /**
     * @throws Exception
     */
    public function limit($start, $offset): QueryBuilder
    {
        if (empty($this->query)) {
            $this->reset();
        }
        // TODO: Implement limit() method.
        if ($this->query->type != 'select') {
            throw new \Exception("LIMIT can only be added to SELECT");
        }
        $this->query->limit = " LIMIT " . $start . ", " . $offset;

        return $this;
    }

    public function getSql(): string
    {
        // TODO: Implement getSql() method.
        $query = $this->query;

        $sql = 'select ';

        if (!empty($query->field)) {
            $sql .= $query->field;
        }
        if (!empty($query->table)) {
            $sql .= " from " . $query->table;
        }

        if (!empty($query->where)) {
            $sql .= " WHERE " . implode(' AND ', $query->where);
        }

        if (isset($query->limit)) {
            $sql .= $query->limit;
        }

        return $sql . ";";
    }

    public function reset(): void
    {
        // TODO: Implement reset() method.
        $this->query = new \stdClass();
    }
}
  • 别的查询构造器
class OtherQueryBuilder implements QueryBuilder
{

}
  • 测试调用
$mysql = new MysqlQueryBuilder();

$sql = $mysql->table("users")->select(['id', 'name', 'email'])->where('id', 5)
    ->where('email', '123@test.com')
    ->limit(0, 10)
    ->getSql();

var_dump($sql);
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值