ADODB类使用


Posted in PHP onNovember 25, 2006

MySQL的例子
PHP中最通用的数据库是MySQL,所以我想你会喜欢下面的程序代码,它连结到 localhost 的 MySQL 服务器,数据库名称是 mydab,并且执行一个 SQL 的 select 指令查询,查询结果会一列列地印出来。

$db = mysql_connect("localhost", "root", "password");
mysql_select_db("mydb",$db);

$result = mysql_query("SELECT * FROM employees",$db);
if ($result === false) die("failed");

while ($fields = mysql_fetch_row($result)) {
 for ($i=0, $max=sizeof($fields); $i < $max; $i++) {
        print $fields[$i].' ';
 }
 print "<br>n";
}

上列的程序代码用颜色标出分段,第一段是连结的部分,第二段是执行SQL指令,最后一段则是显示字段,while循环扫描结果的每一列,而for循环扫描到每列的字段。

接下来是以ADODB的程序代码得到同样的结果:

 include("adodb.inc.php");
 $db = NewADOConnection('mysql');
 $db->Connect("localhost", "root", "password", "mydb");

 $result = $db->Execute("SELECT * FROM employees");
 if ($result === false) die("failed");
 
 while (!$result->EOF) {
    for ($i=0, $max=$result->FieldCount(); $i < $max; $i++)
           print $result->fields[$i].' ';
    $result->MoveNext();
    print "<br>n";
 }

现在改成指向Oracle数据库,程序代码只要修改第二行成为 NewADOConnection('oracle'),让我们看一下完整的程序代码...

与数据库连结

include("adodb.inc.php");
$db = NewADOConnection('mysql');
$db->Connect("localhost", "root", "password", "mydb");

连结的程序代码比起原来MySQL的程序代码有老练一些,因为我们正是需要更老练些。在ADODB我们使用对象导向的方法来管理多样数据库的复杂性,我们用不同类(class)来控制不同数据库。假如你不熟悉对象导向程序设计,别担心!所有的复杂事情都隐藏在 NewADOConnection() 函数之后。

为了节省内存,我们只加载与你所连结数据库相关的PHP程序代码,我们通过调用NewADOConnection(databasedriver)来完成这件事,合法的数据库驱动程序包含 mysql,mssql,oracle,oci8,postgres,sybase,vfp,access,ibase 以及许多其它的驱动程序。

接着我们通过调用 NewADOConnection() 来从连结类别产生一个新的对象实体,最后我们使用 $db->Connect() 来连结数据库。

执行SQL指令

$result = $db->Execute("SELECT * FROM employees");
if ($result === false) die("failed");

直接传送SQL指令到服务器,当成功执行之后,Execute()将传回一个recordset对象,你可以如同上面所列来检查$result。

一个初学者容易混淆的议题是,在ADODB有两种类型的对象,连结对象以及recordset对象,我们何时用这些对象呢?

连结对象($db)是负责连结数据库,格式化你的SQL查询。而recordset对象($result)则是负责撷取结果并将响应数据规格化成文字或数组。

唯一我需要增加的事情是,ADODB提供许多有用的函数来让INSERT及UPDATE指令更容易些,这点我们在进阶的章节会提到。

撷取资料

while (!$result->EOF) {
   for ($i=0, $max=$result->FieldCount(); $i < $max; $i++)
       print $result->fields[$i].' ';
   $result->MoveNext();
   print "<br>n";
}

前面取得数据的范例很像从档案读数据,在每一行我们首先检查是否到了档案的结尾(EOF),若还没到结尾,循环扫过每列中的字段,然后移到下一行(MoveNext)接着重复同样的事情。

$result->fields[]数组是由PHP数据库延伸系统所产生的,有些数据库延伸系统并不会以字段名称建立该数组的索引,要强迫以名称排序索引该数组,使用$ADODB_FETCH_MODE的通用变量。

        $ADODB_FETCH_MODE = ADODB_FETCH_NUM;
        $rs1 = $db->Execute('select * from table');
        $ADODB_FETCH_MODE = ADODB_FETCH_ASSOC;
        $rs2 = $db->Execute('select * from table');
        print_r($rs1->fields); // shows array([0]=>'v0',[1] =>'v1')
        print_r($rs2->fields); // shows array(['col1']=>'v0',['col2'] =>'v1')

如同你所见的上面例子,两个recordset储存并使用不同的取用模式,当recordset由Execute()产生后再设定$ADODB_FETCH_MODE。

ADOConnection

连结到数据库的对象,执行SQL指令并且有一组工具函数来标准格式化SQL指令,比如关联与日期格式等指令。

其它有用的函数

$recordset->Move($pos)卷动目前的数据列,ADODB支持整个数据库往前卷动,有一些数据库并不支持往后的卷动,这倒不会是个问题,因为你能够用暂存纪录到快取来仿真往后卷动。

$recordset->RecordCount()传回SQL指令存取到的纪录笔数,有些数据库会因为不支持而传回-1。

$recordset->GetArray()以数组的方式传回结果。

rs2html($recordset)函数将传进的recordset转为HTML的表格格式。下例中以粗体字显示相关用法:

include('adodb.inc.php');
include('tohtml.inc.php'); /* includes the rs2html function */
$conn = &ADONewConnection('mysql');
$conn->PConnect('localhost','userid','password','database');
$rs = $conn->Execute('select * from table');
rs2html($rs); /* recordset to html table */

还有许多其它有用的函数列示在文件之中,可从下列网址查得 http://php.weblogs.com/adodb_manual

进阶题材

新增及更新

假设你要新增下列数据到数据库中。

ID = 3
TheDate=mktime(0,0,0,8,31,2001) /* 31st August 2001 */
Note= sugar why don't we call it off

当你改用别的数据库,可能就没办法新增数据。

第一个问题是,每一个数据库各自有不同的内定日期格式,MySQL使用 YYYY-MM-DD 格式,而其它数据库则有不同的内定格式,ADODB提供DBDate()函数来转换不同数据库之间的日期内定格式。

次一个问题是单引号(don't)的表示法,在MySQL可以直接使用单引号(don't),但在其它数据库如Sybase、Access、 Microsoft SQL Server,则用两个单引号表示(don''t),qstr()函数可以解决此问题。

我们如何使用这些函数?就像这样:

$sql = "INSERT INTO table (id, thedate,note) values ("
   . $ID . ','
   . $db->DBDate($TheDate) .','
   . $db->qstr($Note).")";
$db->Execute($sql);

ADODB还有$connection->Affected_Rows()函数,传回受最后update或delete指令影响的数据列数,及$recordset->Insert_ID()函数,传回最后因insert指令而自动产生的数据列编号,预先提醒大家,没有任何数据库有提供这两个函数。

MetaTypes

你可以得到关于字段的更多信息,透过recordset的方法FetchField($fieldoffset)传回对象的3个属性:name,type,max_length。

举例说明:

$recordset = $conn->Execute("select adate from table");
$f0 = $recordset->FetchField(0);

结果$f0->name的内容是'adata',$f0->type将是'date',假如max_length不知道,其内容将会是-1。

处理不同数据库的一个问题是,每一个数据库对于相同的数据型态会有不同的称呼,比如timestamp型态在某数据库中称为datetime,而另一个数据库则称为time,所以ADODB提供MetaType($type,$max_length)函数来标准化下列的数据型态:

C: character and varchar types
X: text or long character (eg. more than 255 bytes wide).
B: blob or binary image
D: date
T: timestamp
L: logical (boolean)
I: integer
N: numeric (float, double, money)

在前面的例子中,

$recordset = $conn->Execute("select adate from table");
$f0 = $recordset->FetchField(0);
$type = $recordset->MetaType($f0->type, $f0->max_length);
print $type; /* should print 'D' */

Select指令的Limit及Top支持

ADODB有个$connection->SelectLimit($sql,$nrows,$offset)函数让你撷取recordset的部分集合,这是采用Microsoft产品中的SELECT TOP用法,及PostgreSQL与MySQL中的SELECT...LIMIT用法的优点,即使原来的数据库并没有提供此用法,本函数也仿真提供该使用方式。

快取支援

ADODB允许你在你的档案系统中暂存recordset的数据,并且在$connection->CacheExecute($secs2cache,$sql)及 $connection->CacheSelectLimit($secs2cache,$sql,$nrows,$offset)等设定的时间间隔到达之后,才真正去做数据库的查询以节省时间。

PHP4 Session支持

ADODB也支持PHP4 session handler,你可以存放你的session变量在数据库中,相关功能请参考 http://php.weblogs.com/adodb-sessions

鼓励商业使用

假如你计划写商用的PHP应用软件来销售,你也可以使用ADODB,我们依据GPL来出版ADODB,也就是说你可以合法地在商用应用软件中引用,并保有你程序代码的所有权。强烈地鼓励ADODB的商业应用,我们自己内部也正以这个理由如此使用中。

PHP 相关文章推荐
给apache2.2加上mod_encoding模块後 php5.2.0 处理url出现bug
Apr 12 PHP
ionCube 一款类似zend的PHP加密/解密工具
Jul 25 PHP
探讨:array2xml和xml2array以及xml与array的互相转化
Jun 24 PHP
PHP反向代理类代码
Aug 15 PHP
PHP+Ajax检测用户名或邮件注册时是否已经存在实例教程
Aug 23 PHP
PHP清除数组中所有字符串两端空格的方法
Oct 20 PHP
discuz目录文件资料汇总
Dec 30 PHP
php单一接口的实现方法
Jun 20 PHP
深入理解PHP之OpCode原理详解
Jun 01 PHP
完美解决在ThinkPHP控制器中命名空间的问题
May 05 PHP
PHP面向对象五大原则之开放-封闭原则(OCP)详解
Apr 04 PHP
PHP htmlentities()函数用法讲解
Feb 25 PHP
smarty静态实验表明,网络上是错的~呵呵
Nov 25 #PHP
PHP动态变静态原理
Nov 25 #PHP
smarty 原来也不过如此~~呵呵
Nov 25 #PHP
用PHP的ob_start();控制您的浏览器cache!
Nov 25 #PHP
PHP 常见郁闷问题答解
Nov 25 #PHP
PHP通用检测函数集合
Nov 25 #PHP
用PHP实现将GB编码转换为UTF8
Nov 25 #PHP
You might like
PHP5中MVC结构学习
2006/10/09 PHP
php中explode的负数limit用法分析
2015/02/27 PHP
PHP+MySQL实现模糊查询员工信息功能示例
2018/06/01 PHP
JavaScript 函数调用规则
2009/09/14 Javascript
JavaScript的public、private和privileged模式
2009/12/28 Javascript
jquery将一个表单序列化为一个对象的方法
2013/12/02 Javascript
Js实现网页键盘控制翻页的方法
2014/10/30 Javascript
jQuery mobile 移动web(4)
2015/12/20 Javascript
浅谈使用splice函数对数组中的元素进行删除时的注意事项
2016/12/04 Javascript
vue.js指令和组件详细介绍及实例
2017/04/06 Javascript
vue.js前后端数据交互之提交数据操作详解
2018/04/24 Javascript
uni-app 支持多端第三方地图定位的方法
2020/01/03 Javascript
JavaScript字符和ASCII实现互相转换
2020/06/03 Javascript
Python使用SocketServer模块编写基本服务器程序的教程
2016/07/12 Python
深入浅出分析Python装饰器用法
2017/07/28 Python
在Python web中实现验证码图片代码分享
2017/11/09 Python
TensorFlow模型保存/载入的两种方法
2018/03/08 Python
selenium处理元素定位点击无效问题
2019/06/12 Python
使用OpCode绕过Python沙箱的方法详解
2019/09/03 Python
Python多线程爬取豆瓣影评API接口
2019/10/22 Python
Django框架安装方法图文详解
2019/11/04 Python
Python TKinter如何自动关闭主窗口
2020/02/26 Python
解决keras加入lambda层时shape的问题
2020/06/11 Python
Python面向对象特殊属性及方法解析
2020/09/16 Python
纯DOM+CSS3实现简单的小风车动画
2016/09/27 HTML / CSS
CSS3 简单又实用的5个属性
2010/03/04 HTML / CSS
css3中新增的样式使用示例附效果图
2014/08/19 HTML / CSS
为什么要用EJB
2014/04/17 面试题
竞选班长演讲稿
2013/12/30 职场文书
后进生转化工作制度
2014/01/17 职场文书
上课玩手机检讨书
2014/02/08 职场文书
班班通校本培训方案
2014/03/12 职场文书
《小猪家的桃花树》教学反思
2014/04/11 职场文书
大学奖学金获奖感言
2014/08/15 职场文书
党的群众路线教育实践活动对照检查材料(四风)
2014/09/27 职场文书
解析探秘fescar分布式事务实现原理
2022/02/28 Java/Android