编程开发 > ACCESS > 文章内容

带数据缓存的ACCESS数据库操作类(二)

2010-12-29编辑:dan

代码:

以下为引用的内容:

<?php
class access
{
 /**
  * 声明存储查询结果ID的数组,数据库连接ID,存储分页信息的数组,缓存数据读取偏移量
  */
 public $resultId, $linkId, $pageMsg, $offset;
 /**
  * 声明显示错误消息的页面地址
  */
 public $errPage = '';
 /**
  * 声明数据库路径,此路径需为绝对路径
  */
 public $dbPath = '';
 
 /**
  * 缓存存储路径
  */
 public $cachePath = '';
 
 /**
  * 缓存声明周期,设为0则不适用缓存
  */
 public $cacheLifeTime = 3600;
 
 /**
  * 当使用分页查询时,最多缓存多少页
  */
 public $cacheLimitMax = 100;
 
 /**
  * 建立数据库连接
  *
  * 说明:
  * 此数据库类无构造函数,在声明新类之后,需手动运行此函数
  */
 public function connect()
 {
  $dsn = 'DRIVER={Microsoft Access Driver (*.mdb)}; DBQ='.$this->dbPath;
  $this->linkId = odbc_connect($dsn,'','',SQL_CUR_USE_ODBC);
  $this->linkId || $this->setError('Connect database defeat!');
 }
 
 /**
  * 执行一条SQL语句
  *
  * 参数:
  * $sql       要执行的SQL语句
  * $resultId  查询结果的ID,当执行一条不需返回的SQL语句,如删除,更新等时,该参数可省略
  */
 public function query($sql ,$resultId = '__id__')
 {
  $this->resultId[$resultId] = odbc_exec($this->linkId,$sql);
  $this->resultId[$resultId] || $this->setError('Carries out the SQL defeat!');
 }
 
 /**
  * 从查询结果集中读取一条记录,并返回为数组
  *
  * 参数:
  * $resultId  查询结果的ID
  */
 public function record($resultId)
 {
  if (is_array($this->resultId[$resultId]))
  {
   $offset = $this->offset[$resultId]; $this->offset[$resultId]++;
   return $this->resultId[$resultId][$offset];
  }
  return odbc_fetch_array($this->resultId[$resultId]);
 }
 
 /**
  * 从查询结果集中读取一条记录,并注册为类的属性,属性名为字段名
  *
  * 参数:
  * $resultId  查询结果ID
  */
 public function recordObj($resultId)
 {
  if (is_array($this->resultId[$resultId]))
  {
   $rowArray = $this->resultId[$resultId][$this->offset[$resultId]];
   $this->offset[$resultId]++;
  } else {
   $rowArray = $this->record($resultId);
  }
  for (reset($rowArray);$key = key($rowArray);next($rowArray)) $this->$key = $rowArray[$key];
 }
 
 /**
  * 获取一个查询结果集的记录数
  *
  * 参数:
  * $resultId  查询结果ID
  */
 public function rowsNum($resultId)
 {
  return odbc_num_rows($this->resultId[$resultId]);
 }
 
 /**
  * 获取表中符合条件的记录总数
  *
  * 参数:
  * $table      表明
  * $primary    主键,提供一个主键时可提高性能
  * $condition  查询条件,留空时将返回表中的记录总数
  */
 public function rowsTotal($table, $primary = '*', $condition = '')
 {
  $sql = 'select ('.$primary.') from '.$table.($condition ? ' where '.$condition : '');
  $rowsTotal = odbc_result(odbc_exec($this->linkId,$sql),1);
  $rowsTotal >= 0 || $this->setError('Gains the record total defeat!');
  return (int)$rowsTotal;
 }
 
 /**
  * 释放一个查询结果
  *
  * 参数:
  * $resultId  查询结果ID
  */
 public function resultFree($resultId)
 {
  odbc_free_result($this->resultId[$resultId]) || $this->setError('Release result defeat!');
 }
 
 /**
  * 释放所有查询结果
  */
 public function allResultFree()
 {
  for (reset($this->resultId);$key = key($this->resultId);next($this->resultId)) '__id__' == $key || $this->resultFree($key);
 }
 
 /**
  * 释放所有查询结果并关闭数据库连接
  */
 public function close()
 {
  $this->allResultFree(); odbc_close($this->linkId);
 }
 
 /**
  * 数据库查询
  *
  * 参数:
  * $resultId  查询结果ID
  * $table     所要查询的数据表
  * $fields    需要返回的字段,省略时将返回所有字段
  * $condition 查询条件,省略时,将返回表中的所有记录
  */
 public function select($resultId, $table, $fields = '*', $condition = '')
 {
  if ($this->cacheLifeTime)
  {
   $cachePath = $this->cachePath.$table.md5($fields.$condition).'.php';
   if (time() - @filemtime($cachePath) < $this->cacheLifeTime)
   {
    include $cachePath; $this->resultId[$resultId] = $dataCache;
    $this->offset[$resultId] = 0; return;
   } else {
    $writeCache = true;
   }
  }
  $condition && $condition = 'order ' == substr($condition,0,6) ? $condition : ' where '.$condition;
  $this->query('select '.$fields.' from '.$table.$condition,$resultId);
  $writeCache && $this->writeCache($cachePath,$resultId);
 }
 
 /**
  * 插入记录
  *
  * 参数:
  * $table     表明
  * $rowArray  二维数组,索引为字段名
  */
 public function insert($table,$rowArray)
 {
  $fields = $values = '';
  for (reset($rowArray); $key = key($rowArray);next($rowArray))
  {
   $fields .= ','.$key; $values .= ',\''.$rowArray[$key].'\'';
  }
  $this->query('insert into '.$table.'('.substr($fields,1).') values('.substr($values,1).')');
 }
 
 /**
  * 更新一条记录
  *
  * 参数:
  * $table      表名
  * $rowArray   二维数组,索引为字段名
  * $condition  更新条件
  */
 public function update($table,$rowArray,$condition)
 {
  $fields = '';
  for (reset($rowArray);$key = key($rowArray);next($rowArray)) $fields .= ','.$key.'=\''.$rowArray[$key].'\'';
  $this->query('update '.$table.' set '.substr($fields,1).' where '.$condition);
 }
 
 /**
  * 删除记录
  *
  * 参数:
  * $table      表明
  * $condition  删除条件,当省略时,删除表中的所有记录
  */
 public function delete($table,$condition = '')
 {
  $this->query('delete from '.$table.($condition ? ' where '.$condition : ''));
 }
 
 /**
  * 输出数据列表
  *
  * 参数:
  * $resultId    查询结果ID
  * $rowHtml     列表的行HTML代码
  * $everyOther  每隔几行插入$insertHtml
  * $insertHtml  需要插入的HTML
  *
  * $rowHtml的编写规则:
  * <td>{$name}</td><td>{date('Y-m-d',strtotime($addtime))}</td>
  * 需要输出的字段或用来格式化字段的函数需用{和}包括
  * 变量名使用字段名
  */
 public function displayList($resultId,$rowHtml,$everyOther = '',$insertHtml = '')
 {
  $rowHtml = preg_replace('/\$([A-Za-z0-9_]+)/','$rowArray[\'\\1\']',$rowHtml);
  $rowHtml = 'echo \''.str_replace(array('{','}'),array('\',',',\''),$rowHtml).'\'';
  $i = 1;
  while ($rowArray = $this->record($resultId))
  {
   eval($rowHtml);
   if ($everyOther == $i) { echo $insertHtml; $i = 1; }
   $i = $i + 1;
  }
 }
 
 /**
  * 分页查询函数
  *
  * 参数:
  * $resultId  查询结果ID
  * $table     所要查询的数据表名
  * $fields    需要返回的字段
  * $primary   用来排序的字段
  * $page      查询第几页
  * $pageSize  每页记录数
  * $condition 查询条件,默认为空
  * $order     排序方式,0为正序,1为倒序,默认为1
  *
  * 说明:
  * 此函数会将与分页相关的信息存储于$this->pageMsg[$resultId]中
  * 这是一个一维数组,具有5个值,分别为:记录总数,总页数,当前页记录数,当前第几页,每页多少条记录
  * 可利用这些信息编写自己的分页样式,不需另外计算
  */
 public function limit($resultId,$table,$fields,$primary,$page,$pageSize,$condition = '',$order = 1)
 {
  isset($this->pageMsg[$resultId][0]) || $this->pageMsg[$resultId][0] = $this->rowsTotal($table,$primary,$condition);
  $this->pageMsg[$resultId][1] = ceil($this->pageMsg[$resultId][0]/$pageSize);
  $page > $this->pageMsg[$resultId][1] && $page = $this->pageMsg[$resultId][1];
  $this->pageMsg[$resultId][2] = $page == $this->pageMsg[$resultId][1] ? ($this->pageMsg[$resultId][0]-($page-1)*$pageSize) : $pageSize;
  $this->pageMsg[$resultId][3] = $page;
  $this->pageMsg[$resultId][4] = $pageSize;
  if ($this->cacheLifeTime && $page <= $this->cacheLimitMax)
  {
   $cachePath = $this->cachePath.$table.'_'.$page.'.php';
   if (time() - @filemtime($cachePath) < $this->cacheLifeTime)
   {
    include $cachePath; $this->resultId[$resultId] = $dataCache;
    $this->offset[$resultId] = 0; return;
   } else $writeCache = true;
  }
  if ($order)
  {
   $mark = '<'; $min = 'min'; $order = ' order by '.$primary.' desc';
  } else {
   $mark = '>'; $min = 'max'; $order = '';
  }
  $sql = 'select top '.$this->pageMsg[$resultId][2].' '.$fields.' from '.$table;
  if (1 == $page)
  {
   $sql .= ($condition ? ' where '.$condition : '').$order;
  } else {
   $sql .= ' where '.$primary.$mark.'(select '.$min.'('.$primary.') from (select top '.($page-1)*$pageSize;
   $sql .= ' '.$primary.' from '.$table.$order.')) '.($condition ? 'and '.$condition : '').$order;
  }
  $this->query($sql,$resultId);
  $writeCache && $this->writeCache($cachePath,$resultId);
 }
 
 public function displayLimit($resultId,$linkHtml,$style = 2,$recordName = '条记录')
 {
     if (2 == $style)
     {
      echo '共&nbsp;<strong>',$this->pageMsg[$resultId][0],'</strong>&nbsp;',$recordName,' ';
     }
     echo '<a href=',str_replace('*','1',$linkHtml),'>首页</a>&nbsp;';
     if (1 == $this->pageMsg[$resultId][3])
     {
      echo '上一页&nbsp;';
     } else {
      echo '<a href=',strtr('*',$this->pageMsg[$resultId][3]-1,$linkHtml),'>上一页</a>&nbsp;';
     }
     if ($this->pageMsg[$resultId][3] == $this->pageMsg[$resultId][1])
     {
      echo '下一页';
     } else {
      echo '<a href=',strtr('*',$this->pageMsg[$resultId][3]+1,$linkHtml),'>下一页</a>';
     }
     echo '&nbsp;<a href=',strtr('*',$this->pageMsg[$resultId][1],$linkHtml);
     echo '>尾页</a>&nbsp;页次:<strong><font color=#ff0000>';
     echo $this->pageMsg[$resultId][3],'</font>/',$this->pageMsg[$resultId][1],'</strong>页';
     if (2 == $style)
     {
      echo ' <strong>',$this->pageMsg[$resultId]['e'],'</strong>',$recordName,'/页&nbsp;转到';
      echo ':<select name=page size=1 onchange="javascript:window.location=';
      echo 'this.options[this.selectedIndex].value;" style=font-size:12px;height=18px>';
      for ($i=1;$i<=$this->pageMsg[$resultId][1];$i++)
      {
       echo '<option value=\'',strtr('*',$i,$linkHtml);
       echo $this->pageMsg[$resultId][3] == $i ? '\' selected ' : '\'','>第',$i,'页</option>';
      }
      echo '</select>';
     }
 }
 
 /**
  * 将查询结果输入缓存
  *
  * 参数:
  * $cachePath  缓存路径
  * $resultId   查询结果ID
  */
 private function writeCache($cachePath,$resultId)
 {
  $cacheContent = '';
  while ($rowArray = odbc_fetch_array($this->resultId[$resultId]))
  {
   $cacheContent .= '$dataCache[]=array('.$this->rowToStr($rowArray).');';
  }
  file_put_contents($cachePath,'<?php '.$cacheContent.' ?>');
  include $cachePath; $this->resultId[$resultId] = $dataCache;
  $this->offset[$resultId] = 0;
 }
 
 /**
  * 将数组转换为一个二维数组结构的字符串
  *
  * 参数:
  * $rowArray  数组
  */
 private function rowToStr($rowArray)
 {
  for (reset($rowArray);$key = key($rowArray);next($rowArray))
  {
   $rowStr .= ',\''.$key.'\'=>\''.strtr($rowArray[$key],'\'','\\\'').'\'';
  }
  return substr($rowStr,1);
 }
 
 /**
  * 调用错误消息页面,完成错误消息的显示
  *
  * 参数:
  * $msg  错误消息
  */
 public function setError($msg)
 {
  include $this->errPage;
 }
}
?>

带数据缓存的ACCESS数据库操作类(一)

热点推荐

登录注册
触屏版电脑版网站地图