奶瓶的文本数据库操作类
未经测试,收藏一下
<?php
//=============================================================================//
// 程序名称:文本数据库操作类
// 程序作者:我是一只鱼(QQ:454813812)
// 写作时间:2005-03-12
//=============================================================================//
class TxtDb{
var $dataBase;
var $dataRows;
var $dataCache;
var $dataError;
function TxtDb($dataBase = "data"){
$this->dataBase = $dataBase;
$this->dataCache = "cache";
$this->dataError = null;
}
function insert($tableName,$args){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r+")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$result="1",$length=0,$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$length += $value;
if(!array_key_exists($key,$args)){
$result .= str_pad("",$value);
}else if(strlen($args[$key])>$value){
$this->dataError = "用户字段太长 '$key' 错误";
fclose($fp);
return false;
}else{
$result .= str_pad($args[$key],$value);
}
}
fseek($fp,0,SEEK_END);
fwrite($fp,$result);
fclose($fp);
return true;
}
}
function update($tableName,$rows,$args){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r+")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$result="1",$length=0,$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$length += $value;
if(!array_key_exists($key,$args)){
$result .= str_pad("",$value);
}else if(strlen($args[$key])>$value){
$this->dataError = "用户字段太长 '$key' 错误";
fclose($fp);
return false;
}else{
$result .= str_pad($args[$key],$value);
}
}
if(fseek($fp,$rows*strlen($result)+200,SEEK_SET) == 0){
fwrite($fp,$result);
fclose($fp);
return true;
}else{
fclose($fp);
$this->dataError = "记录更新失败,数据定位失败";
return false;
}
}
}
function select($table,$rows){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$result="1",$length=0,$head=array(),$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$head[$key] = $value;
$length += $value;
}
if(fseek($fp,$rows*($length+1)+200,SEEK_SET) == 0){
$result = array('rows'=>$rows);
foreach($head AS $key=>$value)$result[$key] = fread($fp,$value);
fclose($fp);
return $result;
}else{
fclose($fp);
$this->dataError = "记录更新失败,数据定位失败";
return false;
}
}
}
function getAll($tableName,$query,$order = "0,desc",$limit = "0,100000"){
$cacheFile = $this->dataBase."/".$this->dataCache."/".md5("$tableName:$query:$order").".tdc";
list($order,$ordertype,$limit,$end) = explode(",",$order.','.$limit);
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$length=0,$result="1",$head=array(),$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$head[$key] = $value;
$length += $value;
}
if(@filemtime($cacheFile) > time()-1000){
if($fp1 = fopen($cacheFile,"r")){
$result = unpack("Vrows",fread($fp1,4));
$this->dataRows = $result['rows'];
if(fseek($fp1,($limit+1)*4,SEEK_SET) == 0){
$result = unpack("V*",fread($fp1,$end*4));
fclose($fp1);
}else{
fclose($fp);
fclose($fp1);
return false;
}
}else{
$this->dataError = "缓存文件打开错误";
fclose($fp);
fclose($fp1);
return false;
}
}else if(fseek($fp,200,SEEK_SET) == 0){
$i = 0;
foreach($head AS $key=>$value){
$query = str_replace("@$key","@".$i++,$query);
}
$result = array();
preg_match_all('/@(\d+)/si',$query,$tmp);
$tmp[1][]= $order;
$query = preg_replace('/@(\d+)/si','$row[\1]',$query);
$execute = '$i=0;while(true){if(strlen($type=fread($fp,1))!=1)break;$row=array(\'rows\'=>$i++);';
for($i=0,$id=empty($tmp[1])?100:max($tmp[1]),$sum=0,$values=array_values($head);$i<count($head);$i++){
$sum += $values[$i];
$execute .= '$row[]=trim(fread($fp,'.$values[$i].'));';
if($id <= $i){
$execute .= 'fseek($fp,'.($length-$sum).',SEEK_CUR);';
break;
}
}
eval($execute.'if($type==\'1\' && '.$query.'){$result[] = array($i-1,$row[$order]);}}');
usort($result,
create_function('$a,$b',$ordertype=="desc"?'return strcmp($a[1],$b[1]);':'return strcmp($b[1],$a[1]);'));
for($i=0,$tmp='';$i<count($result);$i++){$tmp .= pack("V",$result[$i][0]);}
if($fp1 = fopen($cacheFile,"w")){
fwrite($fp1,pack("V",($this->dataRows = strlen($tmp)/4)).$tmp);
fclose($fp1);
}
$result = unpack("V*",substr($tmp,$limit*4,$end*4));
}else{
fclose($fp);
$this->dataError = "记录查询失败,数据定位失败";
return false;
}
$tmp = $row = array();
foreach($result as $rows){
fseek($fp,$rows*($length+1)+201,SEEK_SET);
foreach($head AS $key=>$value){
$row[$key] = trim(fread($fp,$value));
}
$tmp[] = $row;
}
fclose($fp);
return $tmp;
}
}
function remove($tableName,$query){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$length=0,$result="1",$head=array(),$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$head[$key] = $value;
$length += $value;
}
$i = 0;
foreach($head AS $key=>$value){
$query = str_replace("@$key","@".$i++,$query);
}
$result = array();
preg_match_all('/@(\d+)/si',$query,$tmp);
$tmp[1][]= $order;
$query = preg_replace('/@(\d+)/si','$row[\1]',$query);
$execute = '$i=0;while(true){if(strlen($type=fread($fp,1))!=1)break;$row=array(\'rows\'=>$i++);';
for($i=$rows=0,$id=empty($tmp[1])?100:max($tmp[1]),$sum=0,$values=array_values($head);$i<count($head);$i++){
$sum += $values[$i];
$execute .= '$row[]=trim(fread($fp,'.$values[$i].'));';
if($id <= $i){
$execute .= 'fseek($fp,'.($length-$sum).',SEEK_CUR);';
break;
}
}
$execute .= 'if($type==\'1\' && '.$query.'){fseek($fp,'.(-1*($length+1)).',SEEK_CUR);';
eval($execute.'fwrite($fp,\'0\');$rows++;seek($fp,'.$length.',SEEK_CUR);}}');
if($dp = dir($this->dataBase."/".$this->dataCache)){
while($file = $db->read())if(strstr($file,"tdc"))unlink($this->dataBase."/".$this->dataCache."/$file");
$dp->close();
}
fclose($fp);
return $rows;
}
}
function clean($tableName){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$length=0,$result="1",$head=array(),$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$head[$key] = $value;
$length += $value;
}
if(rewind($this->fp) && $fp1 = fopen($this->dataBase."/".$tableName.".tdb.tmp","w")){
fwrite($fp1,fread($fp,200));
while(strlen($tmp = fread($fp,$length+1))){
($tmp{0} == "1") && fwrite($fp1,$tmp);
}
fclose($fp1);
fclose($fp);
unlink($this->dataBase."/".$tableName.".tdb");
rename($this->dataBase."/".$tableName.".tdb.tmp",$this->dataBase."/".$tableName.".tdb");
if($dp = dir($this->dataBase."/".$this->dataCache)){
while($file = $db->read())if(strstr($file,"tdc"))unlink($this->dataBase."/".$this->dataCache."/$file");
$dp->close();
}
return true;
}else{
fclose($fp);
return false;
}
}
}
function create($tableName,$args){
if(file_exists($this->dataBase."/".$tableName.".tdb")){
$this->dataError = "数据表 $table 已经存在";
}else if($fp = fopen($this->dataBase."/".$tableName.".tdb","w")){
fwrite($fp,str_pad("TDB1.0",20));
fwrite($fp,pack("V*",0,0,0,count($args),array_sum($args)));
$tmp = "";
foreach($args AS $key=>$value)$tmp .= "$key:$value;";
fwrite($fp,str_pad($tmp,160));
fclose($fp);
return true;
}else{
$this->dataError = "数据表建立失败";
return false;
}
}
}
?>
//=============================================================================//
// 程序名称:文本数据库操作类
// 程序作者:我是一只鱼(QQ:454813812)
// 写作时间:2005-03-12
//=============================================================================//
class TxtDb{
var $dataBase;
var $dataRows;
var $dataCache;
var $dataError;
function TxtDb($dataBase = "data"){
$this->dataBase = $dataBase;
$this->dataCache = "cache";
$this->dataError = null;
}
function insert($tableName,$args){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r+")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$result="1",$length=0,$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$length += $value;
if(!array_key_exists($key,$args)){
$result .= str_pad("",$value);
}else if(strlen($args[$key])>$value){
$this->dataError = "用户字段太长 '$key' 错误";
fclose($fp);
return false;
}else{
$result .= str_pad($args[$key],$value);
}
}
fseek($fp,0,SEEK_END);
fwrite($fp,$result);
fclose($fp);
return true;
}
}
function update($tableName,$rows,$args){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r+")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$result="1",$length=0,$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$length += $value;
if(!array_key_exists($key,$args)){
$result .= str_pad("",$value);
}else if(strlen($args[$key])>$value){
$this->dataError = "用户字段太长 '$key' 错误";
fclose($fp);
return false;
}else{
$result .= str_pad($args[$key],$value);
}
}
if(fseek($fp,$rows*strlen($result)+200,SEEK_SET) == 0){
fwrite($fp,$result);
fclose($fp);
return true;
}else{
fclose($fp);
$this->dataError = "记录更新失败,数据定位失败";
return false;
}
}
}
function select($table,$rows){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$result="1",$length=0,$head=array(),$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$head[$key] = $value;
$length += $value;
}
if(fseek($fp,$rows*($length+1)+200,SEEK_SET) == 0){
$result = array('rows'=>$rows);
foreach($head AS $key=>$value)$result[$key] = fread($fp,$value);
fclose($fp);
return $result;
}else{
fclose($fp);
$this->dataError = "记录更新失败,数据定位失败";
return false;
}
}
}
function getAll($tableName,$query,$order = "0,desc",$limit = "0,100000"){
$cacheFile = $this->dataBase."/".$this->dataCache."/".md5("$tableName:$query:$order").".tdc";
list($order,$ordertype,$limit,$end) = explode(",",$order.','.$limit);
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$length=0,$result="1",$head=array(),$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$head[$key] = $value;
$length += $value;
}
if(@filemtime($cacheFile) > time()-1000){
if($fp1 = fopen($cacheFile,"r")){
$result = unpack("Vrows",fread($fp1,4));
$this->dataRows = $result['rows'];
if(fseek($fp1,($limit+1)*4,SEEK_SET) == 0){
$result = unpack("V*",fread($fp1,$end*4));
fclose($fp1);
}else{
fclose($fp);
fclose($fp1);
return false;
}
}else{
$this->dataError = "缓存文件打开错误";
fclose($fp);
fclose($fp1);
return false;
}
}else if(fseek($fp,200,SEEK_SET) == 0){
$i = 0;
foreach($head AS $key=>$value){
$query = str_replace("@$key","@".$i++,$query);
}
$result = array();
preg_match_all('/@(\d+)/si',$query,$tmp);
$tmp[1][]= $order;
$query = preg_replace('/@(\d+)/si','$row[\1]',$query);
$execute = '$i=0;while(true){if(strlen($type=fread($fp,1))!=1)break;$row=array(\'rows\'=>$i++);';
for($i=0,$id=empty($tmp[1])?100:max($tmp[1]),$sum=0,$values=array_values($head);$i<count($head);$i++){
$sum += $values[$i];
$execute .= '$row[]=trim(fread($fp,'.$values[$i].'));';
if($id <= $i){
$execute .= 'fseek($fp,'.($length-$sum).',SEEK_CUR);';
break;
}
}
eval($execute.'if($type==\'1\' && '.$query.'){$result[] = array($i-1,$row[$order]);}}');
usort($result,
create_function('$a,$b',$ordertype=="desc"?'return strcmp($a[1],$b[1]);':'return strcmp($b[1],$a[1]);'));
for($i=0,$tmp='';$i<count($result);$i++){$tmp .= pack("V",$result[$i][0]);}
if($fp1 = fopen($cacheFile,"w")){
fwrite($fp1,pack("V",($this->dataRows = strlen($tmp)/4)).$tmp);
fclose($fp1);
}
$result = unpack("V*",substr($tmp,$limit*4,$end*4));
}else{
fclose($fp);
$this->dataError = "记录查询失败,数据定位失败";
return false;
}
$tmp = $row = array();
foreach($result as $rows){
fseek($fp,$rows*($length+1)+201,SEEK_SET);
foreach($head AS $key=>$value){
$row[$key] = trim(fread($fp,$value));
}
$tmp[] = $row;
}
fclose($fp);
return $tmp;
}
}
function remove($tableName,$query){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$length=0,$result="1",$head=array(),$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$head[$key] = $value;
$length += $value;
}
$i = 0;
foreach($head AS $key=>$value){
$query = str_replace("@$key","@".$i++,$query);
}
$result = array();
preg_match_all('/@(\d+)/si',$query,$tmp);
$tmp[1][]= $order;
$query = preg_replace('/@(\d+)/si','$row[\1]',$query);
$execute = '$i=0;while(true){if(strlen($type=fread($fp,1))!=1)break;$row=array(\'rows\'=>$i++);';
for($i=$rows=0,$id=empty($tmp[1])?100:max($tmp[1]),$sum=0,$values=array_values($head);$i<count($head);$i++){
$sum += $values[$i];
$execute .= '$row[]=trim(fread($fp,'.$values[$i].'));';
if($id <= $i){
$execute .= 'fseek($fp,'.($length-$sum).',SEEK_CUR);';
break;
}
}
$execute .= 'if($type==\'1\' && '.$query.'){fseek($fp,'.(-1*($length+1)).',SEEK_CUR);';
eval($execute.'fwrite($fp,\'0\');$rows++;seek($fp,'.$length.',SEEK_CUR);}}');
if($dp = dir($this->dataBase."/".$this->dataCache)){
while($file = $db->read())if(strstr($file,"tdc"))unlink($this->dataBase."/".$this->dataCache."/$file");
$dp->close();
}
fclose($fp);
return $rows;
}
}
function clean($tableName){
if(!$fp = fopen($this->dataBase."/".$tableName.".tdb","r")){
$this->dataError = "数据表打开失败";
return false;
}else if(!strstr(fread($fp,20),"TDB")){
$this->dataError = "数据库文件被破坏或者格式错误";
fclose($fp);
return false;
}else{
fseek($fp,20,SEEK_CUR);
for($i=0,$length=0,$result="1",$head=array(),$tmp=explode(';',trim(fread($fp,160)));$i<count($tmp)-1;$i++){
list($key,$value) = explode(':',$tmp[$i]);
$head[$key] = $value;
$length += $value;
}
if(rewind($this->fp) && $fp1 = fopen($this->dataBase."/".$tableName.".tdb.tmp","w")){
fwrite($fp1,fread($fp,200));
while(strlen($tmp = fread($fp,$length+1))){
($tmp{0} == "1") && fwrite($fp1,$tmp);
}
fclose($fp1);
fclose($fp);
unlink($this->dataBase."/".$tableName.".tdb");
rename($this->dataBase."/".$tableName.".tdb.tmp",$this->dataBase."/".$tableName.".tdb");
if($dp = dir($this->dataBase."/".$this->dataCache)){
while($file = $db->read())if(strstr($file,"tdc"))unlink($this->dataBase."/".$this->dataCache."/$file");
$dp->close();
}
return true;
}else{
fclose($fp);
return false;
}
}
}
function create($tableName,$args){
if(file_exists($this->dataBase."/".$tableName.".tdb")){
$this->dataError = "数据表 $table 已经存在";
}else if($fp = fopen($this->dataBase."/".$tableName.".tdb","w")){
fwrite($fp,str_pad("TDB1.0",20));
fwrite($fp,pack("V*",0,0,0,count($args),array_sum($args)));
$tmp = "";
foreach($args AS $key=>$value)$tmp .= "$key:$value;";
fwrite($fp,str_pad($tmp,160));
fclose($fp);
return true;
}else{
$this->dataError = "数据表建立失败";
return false;
}
}
}
?>
格式超宽了