用mysql命令行可以锁表,但用php代码操作却锁不了表,怎么回事

用mysql命令行可以锁表,但用php代码操作却锁不了表,怎么回事

我先在 mysql 命令行打入以下命令:

begin;

select id,order_amount from member where username=’abc’ for update ;

打入上面两行以后 , 会员表 member 就锁住了,然后我修改 order_amount 的值就无法修改了,

只有再打入命令 commit;

才可以继续读取这个表和修改这个表。

但是我在php文件中这样运行,却没有任何效果,表也无法锁住,请问是什么原因?

php 代码是这样的:

mysql_select_db(“db2”);

mysql_query(“begin”);

$query = “select id,order_amount from member where username=’abc’ for update “;

echo $query;

$result2 = mysql_query($query);

$r5=mysql_fetch_array($result2);

print_r($r5);

因为在php代码中我并没有运行 mysql_query(“commit”); 因为我想看一下用php代码锁表的效果,但是却没有用。

在上面php代码运行以后,还可以用别的php文件继续修改 order_amount 的值。请问是为什么?

回复讨论(解决方案)

事务默认是自动提交的(每条指令后都自动执行 commit)

即便你关闭了自动提交,也会在关闭数据库连接时,自动 commit

锁表的生命周期是当前连接,连接关闭锁就失效了

所以不是
在上面php代码运行以后 而是 在
上面php代码运行时,别的php文件才不可以修改 order_amount 的值。

php执行结束,事务就结束,自动commit了。所以只在你php执行过程中锁。

如果是这样的话,我有两个文件 a.php 和 b.php 都要 对 order_amount 的值进行查询和修改,但我又想用事务控制他们按先后顺序来执行,不要两个同时查询和修改 order_amount 的值,那该如何办呢?

也就是说 a.php 是加积分的,b.php 是减积分的

但这两个文件是同时在不停的运行的,但 a.php 和 b.php 的结果都会影响到 会员积分总数 order_amount 的值

如果不用事务和锁表处理的话,这两个文件同时进行,肯定会把会员积分总数更新得很乱的,这要如何做呢?

我的目的就是加和减要一个个按先后顺序来,那要如何做呢。

你不是加表锁了吗?

那么 a.php 在运行时,b.php 是不能对 order_amount 修改的

注意:这个运行时,是指 a.php 程序正在运行,即浏览器还没有看到结果

按道理应该是这样的,但我用实际运行测试,运行结果却并不是这样

有个会员表 member , 两个字段: username , order_amount 也就是一个是用户名,一个是用户总积分,当前是400积分

另外有一个队列表 memory 有两个字段: username , add_score , 第一个是用户名,第二个是 增加或减少的积分, add_score 的值有正也有负。

现在要做的实验就是 memory 插入 2000条 记录,其中 1000条 add_score 值是正的,另1000条 add_score 是负的,总正负相加为0

然后我用 b.php 处理队列中的数据,每次读出一条记录,更新到会员总积分中,然后删除队列中的这条记录。

a.php 只是查询会员总积分 ,以及 sum 出队列表的数据总和,再输出。 a.php 和 p.php 都在同时运行。

这样的话,如果输出会员的总积分,无论任何时候,都应该是400 的, 因为队列表中的2000条记录积分总数正负相加为0的

但我做测试的时候,却不是这样,是锁表没有生效吗

下面是 b.php 中的代码:

$query = “select * from memory order by id limit 300 “;

$result = mysql_query($query);

while($r2=mysql_fetch_array($result))

{

mysql_query(“begin”);

$query = “select order_amount from member where username=’$r2[username]’ for update “;

$result2 = mysql_query($query);

if($r5=mysql_fetch_array($result2))

{

$new_score = $r5[‘order_amount’] + $r2[‘add_score’] ;

$sql = “update member set order_amount=$new_score’ where t “;

if($rr = mysql_query($sql))

{

$sql66 = “delete from memory where t “;

if($rr66 = mysql_query($sql66))

{

}

} // if $rr

}// if $r5

if( $r5 and $rr and $rr66 ){

mysql_query(“commit”);

}else{

mysql_query(“rollback”);

}

} // while

Posted in 未分类

发表评论