Heim  >  Artikel  >  Backend-Entwicklung  >  Machen Sie sich in drei Minuten mit der in PHP festgelegten Abfragestruktur vertraut

Machen Sie sich in drei Minuten mit der in PHP festgelegten Abfragestruktur vertraut

醉折花枝作酒筹
醉折花枝作酒筹nach vorne
2021-06-18 17:04:371566Durchsuche

Dieser Artikel führt Sie in die in PHPPHP festgelegte Abfragestruktur ein. Es hat einen gewissen Referenzwert. Freunde in Not können sich darauf beziehen. Ich hoffe, es wird für alle hilfreich sein.

Machen Sie sich in drei Minuten mit der in PHP festgelegten Abfragestruktur vertraut

PDO-Operationen in PHP lernen (4) Abfragestruktursatz

Der letzte Artikel über PDO endet mit der Operation des Abfrageergebnissatzes. Im Datenbankbetrieb haben Abfragen oft einen sehr hohen Anteil. In der täglichen Entwicklung handelt es sich bei den meisten Unternehmen um Unternehmen, die mehr lesen und nicht schreiben können. Daher ist die Beherrschung abfragebezogener Vorgänge ein wichtiger Teil unseres Lernens. Wie MySQL ist auch die Unterstützung von PDO für Abfragen sehr praktisch und schnell. Sie können verschiedene Abfrageanweisungen über einige Funktionen sehr bequem und effizient bedienen.

Wenn wir vorbereitete Anweisungen verwenden, wird die Ergebnismenge der Abfrage im PDOStatement-Objekt gespeichert, nachdem wir zum Ausführen die Funktion „execute()“ verwendet haben. Die Operationen an Daten werden an PHP-Objekte übertragen, daher benötigen wir einige Methoden von PDOStatement, um den Inhalt der Ergebnismenge zu erhalten.

fetch()-Methode

Über die fetch()-Methode erhalten Sie die nächste Zeile der Abfrageergebnismenge.

$stmt = $pdo->prepare("select * from zyblog_test_user");
$stmt->execute();

$row = $stmt->fetch();
print_r($row);
// Array
// (
//     [id] => 1
//     [0] => 1
//     [username] => aaa
//     [1] => aaa
//     [password] => aaa
//     [2] => aaa
//     [salt] => aaa
//     [3] => aaa
// )

Den zurückgegebenen Ergebnissen nach zu urteilen, haben wir das Attribut PDO::ATTR_DEFAULT_FETCH_MODE nicht für das PDO-Objekt angegeben, daher wird das Standardformat PDO::FETCH_BOTH zurückgegeben, d. h. der Feldname und der Index sind gleichzeitig vorhanden. Tatsächlich kann diese Methode den von uns benötigten FETCH_STYLE direkt angeben.

Die Spezifikation des Ergebnismengentyps

$row = $stmt->fetch(PDO::FETCH_ASSOC);
print_r($row);
// Array
// (
//     [id] => 2
//     [username] => bbb
//     [password] => bbb
//     [salt] => 123
// )

$row = $stmt->fetch(PDO::FETCH_LAZY);
print_r($row);
// PDORow Object
// (
//     [queryString] => select * from zyblog_test_user
//     [id] => 3
//     [username] => ccc
//     [password] => bbb
//     [salt] => c3
// )

$row = $stmt->fetch(PDO::FETCH_OBJ);
print_r($row);
// stdClass Object
// (
//     [id] => 4
//     [username] => ccc
//     [password] => bbb
//     [salt] => c3
// )

ist dieselbe wie PDO::ATTR_DEFAULT_FETCH_MODE, der das PDO-Objekt angibt. Wenn Sie die Methode fetch () verwenden, geben Sie den erforderlichen Parameter für den Rückgabeergebnistyp direkt im ersten Parameter der Methode an und realisieren Sie so die Spezifikation von FETCH_STYLE. Die spezifischen unterstützten Formate sind genau die gleichen wie das zuvor erwähnte PDO::ATTR_DEFAULT_FETCH_MODE-Attribut. Sie können es selbst überprüfen.

Alle Daten abrufen

Wie aus dem Code und der Definition ersichtlich ist, dient die fetch()-Methode dazu, die nächste Datenzeile im aktuellen Datensatz abzurufen, genau wie die Cursoroperation der Datenbank. Daher können wir die Ergebnismenge durch Schleifen von fetch() durchlaufen, um alle Ergebnismengendaten zu erhalten.

 while($row = $stmt->fetch()){
    print_r($row);
}
// Array
// (
//     [id] => 2
//     [0] => 2
//     [username] => bbb
//     [1] => bbb
//     [password] => bbb
//     [2] => bbb
//     [salt] => 123
//     [3] => 123
// )
// ……

MySQL unterstützt keine Cursor

Wie oben erwähnt, wird die Cursoroperation von der PDO-Erweiterung unterstützt, es ist jedoch zu beachten, dass die MySQL-Erweiterung diese Operation nicht unterstützt. Daher haben die von uns verwendeten Cursor-bezogenen Eigenschaften keine Auswirkungen auf die MySQL-Bibliothek.

$stmt = $pdo->prepare("select * from zyblog_test_user", [PDO::ATTR_CURSOR => PDO::CURSOR_SCROLL]);
$stmt->execute();

$row = $stmt->fetch(PDO::FETCH_ASSOC, PDO::FETCH_ORI_NEXT);
print_r($row);
// Array
// (
//     [id] => 1
//     [username] => aaa
//     [password] => aaa
//     [salt] => aaa
// )

$stmt = $pdo->prepare("select * from zyblog_test_user", [PDO::ATTR_CURSOR => PDO::CURSOR_SCROLL]);
$stmt->execute();

$row = $stmt->fetch(PDO::FETCH_ASSOC, PDO::FETCH_ORI_LAST);
print_r($row);
// Array
// (
//     [id] => 1
//     [username] => aaa
//     [password] => aaa
//     [salt] => aaa
// )

Wenn es sich um eine Datenbank und Erweiterung handelt, die Cursoroperationen unterstützt, sind die erhaltenen Ergebnisse unterschiedlich, nachdem der zweite Parameter von fetch() im obigen Code angegeben wurde. PDO::FETCH_ORI_NEXT dient dazu, die nächsten Daten des Cursors abzurufen, und PDO::FETCH_ORI_LAST dient dazu, die letzten Daten des Cursors abzurufen. Aber in unserem Test auf MySQL hatten sie keine Wirkung und bekamen trotzdem das nächste Datenelement im Ergebnissatz.

fetchAll()-Methode

Über die fetch()-Methode können wir alle Daten im Ergebnissatz abrufen, es ist jedoch immer noch eine Schleife zum Durchlaufen erforderlich, was immer noch etwas mühsam ist. Tatsächlich hat PDO bereits eine andere Methode für uns vorbereitet, fetchAll(), die ein Array zurückgibt, das alle Zeilen im Ergebnissatz enthält.

$stmt = $pdo->prepare("select * from zyblog_test_user limit 2");
$stmt->execute();

$list = $stmt->fetchAll();
print_r($list);
// Array
// (
//     [0] => Array
//         (
//             [id] => 1
//             [0] => 1
//             [username] => aaa
//             [1] => aaa
//             [password] => aaa
//             [2] => aaa
//             [salt] => aaa
//             [3] => aaa
//         )

//     [1] => Array
//         (
//             [id] => 2
//             [0] => 2
//             [username] => bbb
//             [1] => bbb
//             [password] => bbb
//             [2] => bbb
//             [salt] => 123
//             [3] => 123
//         )

// )

fetchAll() verwendet fetch() intern, um uns dabei zu helfen, die Ergebnismenge zu durchlaufen und sie einem Array zuzuweisen. Wenn wir also fetchAll() erneut ohne re-execute() aufrufen, erhalten wir leere Daten. Weil der Cursor unten angekommen ist.

$list = $stmt->fetchAll();
print_r($list);
// Array
// (
// )

Es unterstützt auch die Angabe von FETCH_STYLE. Genau wie bei der fetch()-Methode können Sie dem ersten Parameter direkt die erforderliche Typkonstante zuweisen.

// PDO::FETCH_ASSOC
$stmt = $pdo->prepare("select * from zyblog_test_user limit 2");
$stmt->execute();

$list = $stmt->fetchAll(PDO::FETCH_ASSOC);
print_r($list);
// Array
// (
//     [0] => Array
//         (
//             [id] => 1
//             [username] => aaa
//             [password] => aaa
//             [salt] => aaa
//         )

//     [1] => Array
//         (
//             [id] => 2
//             [username] => bbb
//             [password] => bbb
//             [salt] => 123
//         )

// )

// PDO::FETCH_COLUMN
$stmt = $pdo->prepare("select * from zyblog_test_user limit 2");
$stmt->execute();

$list = $stmt->fetchAll(PDO::FETCH_COLUMN, 1);
print_r($list);
// Array
// (
//     [0] => aaa
//     [1] => bbb
// )

// PDO::FETCH_CLASS
class User{
    function __construct($a){
        echo $a, PHP_EOL;
    }
}
$stmt = $pdo->prepare("select * from zyblog_test_user limit 2");
$stmt->execute();
$list = $stmt->fetchAll(PDO::FETCH_CLASS, 'User', ['FetchAll User']);
print_r($list);
// FetchAll User
// FetchAll User
// Array
// (
//     [0] => User Object
//         (
//             [id] => 1
//             [username] => aaa
//             [password] => aaa
//             [salt] => aaa
//         )

//     [1] => User Object
//         (
//             [id] => 2
//             [username] => bbb
//             [password] => bbb
//             [salt] => 123
//         )

// )

Sind Sie damit sehr vertraut? Ich werde hier nicht auf Details eingehen. Ich habe schon oft über die Typspezifikation von FETCH_STYLE gesprochen. Ihre Verwendung ähnelt der von fetch() und der query()-Methode im PDO-Objekt. Es unterstützt jedoch auch eine Form des Aufrufs einer Methode in einem Rückruf, um den Datensatz abzurufen.

function getValue(){
    print_r(func_get_args());
}
// Array
// (
//     [0] => 1
//     [1] => aaa
//     [2] => aaa
//     [3] => aaa
// )
// Array
// (
//     [0] => 2
//     [1] => bbb
//     [2] => bbb
//     [3] => 123
// )
$stmt = $pdo->prepare("select * from zyblog_test_user limit 2");
$stmt->execute();
$list = $stmt->fetchAll(PDO::FETCH_FUNC, 'getValue');
print_r($list);
// Array
// (
//     [0] => 
//     [1] => 
// )

In diesem Code verwenden wir PDO::FETCH_FUNC und der zweite Parameter ist ein Methodenname. Auf diese Weise wird jeder Struktursatz als Methodenparameter verwendet, um die angegebene Methode während des Durchlaufs aufzurufen. Wir können den Inhalt dieser Parameter über func_get_args() abrufen. In diesem Code wird die Ergebnismenge nicht über den Rückgabewert der fetchAll()-Methode der Variablen $list zugewiesen. Weil die Daten an die angegebene getValue()-Methode übergeben wurden.

fetchColumn()-Methode

Im obigen Testcode haben wir PDO::FETCH_COLUMN verwendet, um eine bestimmte Datenspalte im Ergebnissatz abzurufen. Es ist nichts Falsches daran, auf diese Weise zu schreiben, aber es gibt einen bequemeren Weg, nämlich die fetchColumn()-Methode, die uns PDOStatment direkt zur Verfügung stellt. Dies entspricht der standardmäßigen Angabe von PDO::FETCH_COLUMN innerhalb der Methode und erfordert nur einen Parameter, nämlich den Spaltenindex.

Es ist zu beachten, dass seine Rückgabe der angegebene Spaltenwert der nächsten Zeile ist, das heißt, er ruft die fetch()-Methode unter der Haube auf. Wenn wir den Inhalt aller angegebenen Spalten in der Ergebnismenge erhalten möchten, müssen wir die Ergebnismenge auf die gleiche Weise wie fetch() durchlaufen.

// fetchColumn
$stmt = $pdo->prepare("select * from zyblog_test_user");
$stmt->execute();
$column = $stmt->fetchColumn(2);
echo $column, PHP_EOL;
// aaa

$column = $stmt->fetchColumn(3);
echo $column, PHP_EOL;
// 123

fetchObject() 方法

fetchObject() 就不用多解释了,它和 fetchColumn() 是类似的,只是返回的是下一行数据的对象格式。同样的,它也是可以传递构造参数的,这点和 PDO 对象的 query() 中指定的 PDO::FETCH_CLASS 格式的使用是一样的。我们在第一篇文章中就有讲解。

// fetchObject
$stmt = $pdo->prepare("select * from zyblog_test_user");
$stmt->execute();
$user = $stmt->fetchObject('User', ['FetchObject User']);
print_r($user);
// FetchObject User
// User Object
// (
//     [id] => 1
//     [username] => aaa
//     [password] => aaa
//     [salt] => aaa
// )

rowCount() 返回查询结果数量

要获得查询的结果集行数就需要我们的 rowCount() 方法了。数据库中不管是查询还是增、删、改操作,都会返回语句执行结果,也就是受影响的行数。这些信息都是通过 rowCount() 这个方法获得的。

查询语句返回行数

需要注意的是,在查询语句中,有些数据是可能返回此语句的行数的。但这种方式不能保证对所有数据有效,且对可移植的应用更不要依赖这种方式。我们如果需要知道当前查询结果的数量,还是通过遍历 fetch() 或者通过 count(fetchAll()) 来根据真实查询到的结果集数量确定这一次查询的真实行数。

其实它就像是 PDO 对象的 exec() 方法所返回的数据。在不使用预处理语句的情况下,直接使用 PDO 的 exec() 方法执行 SQL 语句后,返回的也是语句执行后受影响的行数。

$stmt = $pdo->prepare("select * from zyblog_test_user");
$stmt->execute();
$rowCount = $stmt->rowCount();
echo $rowCount, PHP_EOL;
// 41

增、删、改语句返回受影响的行数

$stmt = $pdo->prepare("insert into zyblog_test_user(username, password, salt) values(?, ?, ?)");
$stmt->execute(['kkk','666','k6']);
$rowCount = $stmt->rowCount();
echo $rowCount, PHP_EOL; // 1
$id = $pdo->lastInsertId();
echo $rowCount, PHP_EOL; // 1

$stmt = $pdo->prepare("update zyblog_test_user set username=? where username = ?");
$stmt->execute(['ccc','cccc']);
$rowCount = $stmt->rowCount();
echo $rowCount, PHP_EOL; // 25

$stmt = $pdo->prepare("update zyblog_test_user set username=? where username = ?");
$stmt->execute(['ccc','cccc']);
$rowCount = $stmt->rowCount();
echo $rowCount, PHP_EOL; // 0

$stmt = $pdo->prepare("delete from zyblog_test_user where username = ?");
$stmt->execute(['ddd']);
$rowCount = $stmt->rowCount();
echo $rowCount, PHP_EOL; // 11

$stmt = $pdo->prepare("delete from zyblog_test_user where username = ?");
$stmt->execute(['ddd']);
$rowCount = $stmt->rowCount();
echo $rowCount, PHP_EOL; // 0

更新和删除操作在数据不存在、没有更新、没有删除的情况下都返回的是 0 。这一点我们也在 PDO 相关的第一篇文章中就说过了,对于业务来说,这种更新或删除到底算是成功还是失败呢?还是大家根据自己的实际业务情况来确定吧!

总结

关于 PDO 和 PDOStatement 相关的内容就学习到这里了。我们完整地梳理了一遍它们两个所有的方法,也都进行了相关的测试。大家在日常使用中可能接触到的并不多,框架都已经为我们封装好了。不过对于学习来说,平常的小测试、小调试完全可以自己手写来加深记忆和理解。在深入理解了这些扩展类的使用方法后,反过来又能帮助我们更加的清楚框架是如何去封装它们的。总之,学习就是不断的从高层到底层,再从底层返回高层,循环往复,才能更加的得心应手。

测试代码:

https://github.com/zhangyue0503/dev-blog/blob/master/php/202009/source/PHP%E4%B8%AD%E7%9A%84PDO%E6%93%8D%E4%BD%9C%E5%AD%A6%E4%B9%A0%EF%BC%88%E5%9B%9B%EF%BC%89%E6%9F%A5%E8%AF%A2%E7%BB%93%E6%9E%84%E9%9B%86.php

推荐学习:php视频教程

Das obige ist der detaillierte Inhalt vonMachen Sie sich in drei Minuten mit der in PHP festgelegten Abfragestruktur vertraut. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme:
Dieser Artikel ist reproduziert unter:segmentfault.com. Bei Verstößen wenden Sie sich bitte an admin@php.cn löschen