自己动手做一个SQL解释器

自己动手做一个SQL解释器
在一些小型的应用中,完全没有必要使用大型数据库软件。自己做一个SQL解释器就能用数据库的方式来管理了。
这个解释器,能解释常用的SQL命令。你可以自行添加其他功能。

 1   
 2class DB_text {   
 3var $conn;   
 4var $classname = "db_text";   
 5var $database;   
 6function on_create() {   
 7}   
 8function connect($database_name) {   
 9$this->database = $database_name;   
10if(! file_exists($database_name)) {   
11$this->conn = array();   
12$this->_close();   
13}   
14$fp = fopen($this->database,"r");   
15$this->conn = unserialize(fread($fp,filesize($this->database)));   
16fclose($fp);   
17}   
18function &query($query) {   
19if(eregi("select ",$query)) return $this->_select($query);   
20if(eregi("insert ",$query)) return $this->_insert($query);   
21if(eregi("delete ",$query)) return $this->_delete($query);   
22if(eregi("update ",$query)) return $this->_update($query);   
23return array();   
24}   
25function fetch_row(&$result) {   
26if(list($key,$value) = each($result))   
27return $value;   
28return false;   
29}   
30function num_rows($result) {   
31return count($result);   
32}   
33  
34/**   
35* query的辅助函数   
36*/   
37function _select($query) {   
38if(eregi("(order by (.+))",$query,$regs)) {   
39$order = $regs[2];   
40$query = eregi_replace($regs[1],"",$query);   
41}   
42if(eregi("(group by (.+))",$query,$regs)) {   
43$group = $regs[2];   
44$query = eregi_replace($regs[1],"",$query);   
45}   
46eregi("select .* from ([0-9a-z_]+) *(where +(.+))?",$query,$regs);   
47if($regs[3] != "") {   
48$keys = $this->_where($regs[3],"\$this->conn[$regs[1]]");   
49while(list($key,$value) = each($keys)) {   
50$rs[] = $this->conn[$regs[1]][$value];   
51}   
52}else {   
53$rs = $this->conn[$regs[1]];   
54}   
55if($order) {   
56sscanf($order,"%s %s",$key,$type);   
57if(empty($type)) $type = "asc";   
58$this->_sort($rs,$key,$type);   
59}   
60return $rs;   
61}   
62function _insert($query) {   
63eregi("insert +into +([0-9a-z_]+) *(.+) *values? *(.+)",$query,$regs);   
64eval("\$key=array$regs[2];");   
65eval("\$value=array$regs[3];");   
66for($i=0;$i

<count($key);$i++) $rs[$key[$i]]="$value[$i];" $this-="">conn[$regs[1]][] = $rs;
$this-&gt;_close();
}
function update($query) {
eregi("update +([0-9a-z
]+) +set (,?.=.*)+( +where +(.+))",$query,$regs);
$regs[2] = eregi_replace(",","=",$regs[2]);
$v = split("=",$regs[2]);
$keys = $this-&gt;_where($regs[4],"$this-&gt;conn[$regs[1]]");
while(list($key,$value) = each($keys)) {
for($i=0;$i<count($v);$i+=2) $this-="">conn[$regs[1]][$value][$v[$i]] = eregi_replace("'","",$v[$i+1]);
}
$this-&gt;_close();
}
function delete($query) {
eregi("delete +from +([0-9a-z
]+) (where +(.+))?",$query,$regs);
$keys = $this-&gt;_where($regs[3],"$this-&gt;conn[$regs[1]]");
while(list($key,$value) = each($keys)) {
unset($this-&gt;conn[$regs[1]][$value]);
}
reset($this-&gt;conn[$regs[1]]);
while(list($key,$value) = each($this-&gt;conn[$regs[1]])) {
$ch[] = $value;
}
$this-&gt;conn[$regs[1]] = $ch;
$this-&gt;_close();
}
function _where($search,$table) {
$search = eregi_replace("\("," ( ",$search);
$search = eregi_replace("\)"," ) ",$search);
$search = eregi_replace("\+"," + ",$search);
$search = eregi_replace("\
"," * ",$search);
while(eregi("^ ",$search,$regs)) {
$search = eregi_replace($regs[1]," $regs[1] ",$search);
}
while(eregi("([--><!--] +=)",$search,$regs)) {
$search = eregi_replace($regs[1],eregi_replace(" ","",$regs[1]),$search);
}
$search = eregi_replace(" "," ",trim($search));
$search = eregi_replace(" and "," && ",$search);
$search = eregi_replace(" or "," || ",$search);
$search = eregi_replace(" = "," == ",$search);
$ar = split(" ",$search);
eval("$t=$table;");

for($i=0;$i<count($ar);$i++) {
if(isset($t[0][$ar[$i]]))
$ar[$i] = "$value[".$ar][$i]."]";
}
$expr = "$expl=(".join(" ",$ar).");";

while(list($key,$value) = each($t)) {
eval($expr);
if($expl)
$keys[] = $key;
}
return $keys;
}
function _sort(&$ar,$key=0,$mode="desc") {
global $cmp_key;
$cmp_key = $key;
if($mode == "asc")
usort($ar,_cmp_asc);
else
usort($ar,_cmp_desc);
}
function _close() {
$fp = fopen($this--->database,"w");
fwrite($fp,serialize($this-&gt;conn));
fclose($fp);
}
}

/** 排序键
*/
$cmp_key = "";

/** 排序用工作函数(降序 由usort()调用)
*/
function _cmp_desc($a,$b) {
global $cmp_key;
if ($a[$cmp_key] == $b[$cmp_key]) return 0;
return ($a[$cmp_key] &gt; $b[$cmp_key]) ? -1 : 1;
}

/** 排序用工作函数(升序 由usort()调用)
*/
function _cmp_asc($a,$b) {
global $cmp_key;
if ($a[$cmp_key] == $b[$cmp_key]) return 0;
return ($a[$cmp_key] &gt; $b[$cmp_key]) ? 1 : -1;
}

1  
2测试例:   
3<pre>   

//require_once "db_text.php";

$conn = new DB_text;
$conn-&gt;connect("text1.txt");

$conn-&gt;query("insert into manage (id,title) values (10,'abcd')");
$conn-&gt;query("insert into manage (id,title) values (2,'43d')");
$conn-&gt;query("insert into manage (id,title) values (20,'tuu')");
$conn-&gt;query("update manage set id=101,test='a' where id=10");
//$conn-&gt;query("delete from manage where id='10'");
//$conn-&gt;query("delete from manage where id=10 or table='code'");

//$rt = $conn-&gt;query("select * from manage where id=101 or table='code' group by 1 order by 1 asc");
$rt = $conn-&gt;query("select * from manage group by 1 order by id desc");

print_r($rt);

1</pre></count($v);$i+=2)></count($key);$i++)>
Published At
Categories with Web编程
Tagged with
comments powered by Disqus