您的位置:首页 > 编程语言 > PHP开发

PHP设计模式-数据访问对象模式

2013-07-28 13:05 676 查看
        在PHP开发中,我们经常会与数据库打交道(本例中以mysql为例),尤其是一些数据库的增删改查操作,是经常要用到的。假定,我们有一个mysql数据库,有服务器名$host, 数据库用户名$user, 数据库密码$pass及数据库$test. 

        现在我们要连接test数据库,并执行一个建表语句,通常会这么

//连接数据库
$conn = mysql_connect($host, $user, $pass);
mysql_select_db($dbName, $conn);

//建立user表
$sql  = "CREATE TABLE user (id PRIMARY KEY, name varchar(32))";
mysql_query($sql, $conn);
        要查询表里的内容,我们会:

//连接数据库
$conn = mysql_connect($host, $user, $pass);
mysql_select_db($dbName, $conn);

$sql = "SELECT * FROM user";
$result = mysql_query($sql, $conn);
$ret = array();
while ($row = mysql_fetch_assoc($result)) {
$ret[] = $row;
}
        我们看到,所有数据库的操作都需要一个连接对象, 连接对象的生成需要数据库的一些基础信息(包括host,用户名,密码和数据库名)。那我们把这一块儿抽象出来:
class Db_Mysql
{

//数据库连接对象
protected $_conn;

//初始化数据库连接
public function __construct($host, $user, $pass, $dbName)
{
$this->_conn = mysql_connect($host, $user, $pass);
mysql_select_db($dbName);
}
}
        这时候我们做任何的操作都只需要对这个连接对象进行操作即可。那我们再回忆一下,其实我们经常对数据库的常用操作有执行sql语句,插入,修改,删除,读取数据。那我们就把这个几个方法也抽象出来。

class Db_Mysql
{

//数据库连接对象
protected $_conn;

//初始化数据库连接
public function __construct($host, $user, $pass, $dbName)
{
$this->_conn = mysql_connect($host, $user, $pass);
mysql_select_db($dbName, $this->_conn);
}

//插入操作
public function insert($data)
{
//传入一个数组,可以插入数据
}

//修改操作
public function update($data, $where)
{
//根据查询条件,修改数据
}

//删除操作
public function delete($where)
{
//根据查询条件,删除数据
}

//执行sql操作
public function execute($sql)
{
$this->getConnection()->query($sql);
}

//根据sql读取数据
public function fetchBySql($sql)
{
$ret = array();
$result = $this->execute($sql);
if (empty($result)) {
return $ret;
}
while ($row = mysql_fetch_assoc($result)) {
$ret[] = $row;
}
return $ret;
}

//获取连接
public function getConnection()
{
return $this->_conn;
}

//获取表名
public function getDbName()
{
return $this->_dbName;
}
}
        由于我们只关心架构,因此,很多地方的具体的实现代码省略掉了。当我们需要对一个数据库进行操作,只要新建一个类,继承Db_Mysql类,就可以无需重复书写大量的数据库操作方法。此时,我们再试着实现刚开始的数据库操作的例子。  
class Test extends Db_Mysql
{

//数据库名
protected $_dbName = "test";

//表名
protected $_tableName = "user";

//初始化
public function __construct($host, $user, $pass)
{
parent::__construct($host, $user, $pass, $this->getDbName());
}
}

//建表
$test = new Test($host, $user, $pass);
$sql  = "CREATE TABLE user (id PRIMARY KEY, name varchar(32))";
$test->execute($sql);

//获取数据
$sql = "SELECT * FROM ".$test->getTableName();
$result = $test->fetchBySql($sql);

//再执行一个sql设置字符集
$sql = "SET NAMES utf8";
$test->execute($sql);
        我们发现,很多的数据库连接的初始化,数据库选择,数据获取等操作,不用再重复书写了。我们把这种对数据的访问的操作的封装叫做数据访问对象模式。其实数据访问对象模式除了用在数据库访问上。还可以用在很多地方,例如:我们要建立一个文件缓存系统,就涉及到缓存的创建,读取,更新等操作,我们也可以把这些操作抽象出来,方便操作,而且不用重复书写代码大量代码,有时候也能起到让调用者无需关心实现细节的目的。

        同时,细心的同学也会发现,其实增删改查这些操作是不应该和Db混在一起的,这些都是表操作。真正的一个好的设计应该是数据库对象,表对象,SQL语句对象,以及数据对象区分开来,尤其是语句对象,它要实现查询域,查询条件,排序方式,分组等条件的抽象。但这一章节,只是为了介绍数据访问对象模式的基本原理。而且本文中很多操作性的代码都省略了。目的只是为了能快速了解这个数据访问对象模式,而免受过多代码的干扰。

        对数据库的操作设计,个人感觉ZendFramewordk的设计很到位。从设计模式的角度上来看,它合理地利用了简单工厂,适配器,数据访问对象,迭代器等模式。有兴趣的朋友可以看一下它的源码,
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: