Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/232.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 为什么需要closeCursor()才能在输出中反映PDO rollback()?_Php_Mysql_Sqlite_Pdo - Fatal编程技术网

Php 为什么需要closeCursor()才能在输出中反映PDO rollback()?

Php 为什么需要closeCursor()才能在输出中反映PDO rollback()?,php,mysql,sqlite,pdo,Php,Mysql,Sqlite,Pdo,在下面的代码中,事务失败并调用回滚 然而,就产出而言: 如果删除closeCursor(),付款人的余额将打印为-200$ 如果我指定closeCursor(),付款人的余额将打印为0,这是预期的行为 这是因为在运行第二个select语句之前,第一个select语句的结果没有被清除 为什么我们需要关闭连接,以便在输出中反映回滚?在这两种情况下,都会调用回滚,因此在DB中指定值0。所以我希望余额打印为0 我看不出关闭连接DB和获取最新DB值之间的关系。Fetch()从DB中获取值,所以如果值为0,

在下面的代码中,事务失败并调用回滚

然而,就产出而言:

如果删除closeCursor(),付款人的余额将打印为-200$

如果我指定closeCursor(),付款人的余额将打印为0,这是预期的行为

这是因为在运行第二个select语句之前,第一个select语句的结果没有被清除

为什么我们需要关闭连接,以便在输出中反映回滚?在这两种情况下,都会调用回滚,因此在DB中指定值0。所以我希望余额打印为0

我看不出关闭连接DB和获取最新DB值之间的关系。Fetch()从DB中获取值,所以如果值为0,“它认为”怎么会是-200

这仅适用于SQLite。无论您是否使用closeCursor(),MySQL都将打印0


瑞安·文森特的上述回复是正确的

所以我指定它是为了将我的问题标记为已解决

谢谢


Qwerty

瑞安·文森特的上述回答是正确的

所以我指定它是为了将我的问题标记为已解决

谢谢


Qwerty

closeCursor()
不会关闭数据库连接。它重置“prepared”语句并刷新所有未完成的行,以便再次执行。谢谢你的意见。什么是“突出的行”?回滚会导致数据库中的余额值为“0”,因此,为什么从连续SQL查询中提取时无法反映该值…?如果没有对查询执行
fetchAll
,则会有缓冲行等待“提取”。当光标关闭时,这些将被清除。
closeCursor()
不会关闭数据库连接。它重置“prepared”语句并刷新所有未完成的行,以便再次执行。谢谢你的意见。什么是“突出的行”?回滚会导致数据库中的余额值为“0”,因此,为什么从连续SQL查询中提取时无法反映该值…?如果没有对查询执行
fetchAll
,则会有缓冲行等待“提取”。光标关闭时,这些选项将被清除。鼓励评论者发布答案,然后接受它(和向上投票)。鼓励评论者发布答案,然后接受它(和向上投票)。
<?php
try {
    require_once '../../includes/pdo_connect.php';
    // Set up prepared statements transfer from one account to another
    $amount = 0;
    $payee = 'John White';
    $payer = 'Jane Black';
    $debit = 'UPDATE savings SET balance = balance - :amount WHERE name = :payer';
    ####1st SQL#### $getBalance = 'SELECT balance FROM savings WHERE name = :payer';  
    $credit = 'UPDATE savings SET balance = balance + :amount WHERE name = :payee';

    $pay = $db->prepare($debit);
    $pay->bindParam(':amount', $amount);
    $pay->bindParam(':payer', $payer);

    $check = $db->prepare($getBalance);
    $check->bindParam(':payer', $payer);

    $receive = $db->prepare($credit);
    $receive->bindParam(':amount', $amount);
    $receive->bindParam(':payee', $payee);

    // Transaction
    $db->beginTransaction();
    $pay->execute();
    if (!$pay->rowCount()) {
        $db->rollBack();
        $error = "Transaction failed: could not update $payer's balance.";
    } else {
        // Check the remaining balance in the payer's account
        $check->execute();
        $bal = $check->fetchColumn();
        ########## $check->closeCursor(); 

        // Roll back the transaction if the balance is negative
        if ($bal < 0) {
            $db->rollBack();
            $error = "Transaction failed: insufficient funds in $payer's account.";
        } else {
            $receive->execute();
            if (!$receive->rowCount()) {
                $db->rollBack();
                $error = "Transaction failed: could not update $payee's balance.";
            } else {
                $db->commit();
            }
        }
    }
} catch (Exception $e) {
    $error = $e->getMessage();
}
?>
<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <title>PDO Transaction</title>
    <link href="../../styles/styles.css" rel="stylesheet" type="text/css">
</head>
<body>
<h1>PDO Transactions</h1>
<?php
if (isset($error)) {
    echo "<p>$error</p>";
}
?>
<table>
    <tr>
        <th>Name</th>
        <th>Balance</th>
    </tr>
            ####2nd SQL####<?php foreach ($db->query('SELECT name, balance FROM savings') as $row) { ?>
    <tr>
        <td><?php echo $row['name']; ?></td>
        <td>$<?php echo number_format($row['balance'], 2); ?></td>
    </tr>
    <?php } ?>
</table>
</body>
</html>