Mysqli или PDO - каковы плюсы и минусы?
В нашем месте мы разделились между использованием mysqli и PDO для таких вещей, как подготовленные заявления и поддержка транзакций. Некоторые проекты используют один, другой - другой. Существует мало реалистичной вероятности того, что мы когда-либо переходим к другой РСУБД.
Я предпочитаю PDO по той единственной причине, что он разрешает именованные параметры для подготовленных операторов, и насколько я знаю, mysqli этого не делает.
Есть ли какие-либо другие плюсы и минусы для выбора одного из них в качестве стандарта, поскольку мы объединяем наши проекты, чтобы использовать только один подход?
Ответы
Ответ 1
Ну, вы можете спорить с объектно-ориентированным аспектом, подготовленными утверждениями, тем фактом, что он становится стандартом и т.д. Но я знаю, что большую часть времени убеждал, что кто-то лучше работает с функцией убийцы. Итак, вот оно:
Действительно хорошая вещь с PDO - вы можете получить данные, автоматически вставляя их в объект. Если вы не хотите использовать ORM (это просто быстрый script), но вам нравится сопоставление объектов, это ДЕЙСТВИТЕЛЬНО круто
class Student {
public $id;
public $first_name;
public $last_name
public function getFullName() {
return $this->first_name.' '.$this->last_name
}
}
try
{
$dbh = new PDO("mysql:host=$hostname;dbname=school", $username, $password)
$stmt = $dbh->query("SELECT * FROM students");
/* MAGIC HAPPENS HERE */
$stmt->setFetchMode(PDO::FETCH_INTO, new Student);
foreach($stmt as $student)
{
echo $student->getFullName().'<br />';
}
$dbh = null;
}
catch(PDOException $e)
{
echo $e->getMessage();
}
Ответ 2
Перемещение приложения из одной базы данных в другую не очень распространено, но рано или поздно вы можете оказаться в другом проекте с использованием другой СУБД. Если вы дома с PDO, тогда, по крайней мере, будет немного меньше, чтобы учиться в этот момент.
Кроме того, я нахожу API PDO немного более интуитивным, и он чувствует себя более объектно ориентированным. mysqli чувствует, что это просто процедурный API, который был объективирован, если вы знаете, что я имею в виду. Короче говоря, я считаю, PDO легче работать, но это, конечно, субъективно.
Ответ 3
Я начал использовать PDO, потому что, по моему мнению, поддержка операторов лучше. Я использую уровень доступа к данным ActiveRecord-esque, и гораздо проще реализовать динамически сгенерированные операторы. Связывание параметров MySQLi должно выполняться одним вызовом функции/метода, поэтому, если вы не знаете до тех пор, пока время выполнения не будет указано, сколько параметров вы хотите привязать, вы вынуждены использовать call_user_func_array()
(я считаю, что имя правой функции ) для выбора. И забудьте про простую динамическую привязку к результату.
Больше всего мне нравится PDO, потому что это очень разумный уровень абстракции. Легко использовать его в полностью абстрактных системах, где вы не хотите писать SQL, но также упрощает использование более оптимизированного, чистого типа запросов, или смешивать и сопоставлять два.
Ответ 4
PDO - это стандарт, это то, что многие разработчики ожидают использовать. mysqli был по сути специальным решением конкретной проблемы, но у него есть все проблемы других библиотек, специфичных для СУБД. PDO - это трудная работа и умное мышление.
Ответ 5
Здесь нужно еще кое-что запомнить: На данный момент (PHP 5.2) библиотека PDO buggy. Он полон странных ошибок. Например: перед сохранением PDOStatement
в переменной переменная должна быть unset()
, чтобы избежать тонны ошибок. Большинство из них были исправлены в PHP 5.3, и они будут выпущены в начале 2009 года в PHP 5.3, у которых, вероятно, будет много других ошибок. Вы должны сосредоточиться на использовании PDO для PHP 6.1, если хотите стабильную версию и использовать PDO для PHP 5.3, если вы хотите помочь сообществу.
Ответ 6
Еще одна заметная (хорошая) разница в PDO заключается в том, что метод PDO::quote()
автоматически добавляет закрывающие кавычки, тогда как mysqli::real_escape_string()
(и аналогий):
PDO:: quote() помещает кавычки вокруг входной строки (если требуется) и вытесняет специальные символы внутри входной строки, используя цитирование стиль, соответствующий базовому драйверу.
Ответ 7
PDO значительно облегчит масштабирование, если ваш сайт/веб-приложение станет действительно таким, как вы можете ежедневно настраивать мастер и подчиненные подключения для распределения нагрузки по базе данных, плюс PHP движется к переходу на PDO в качестве стандарта.
Информация PDO
Масштабирование веб-приложения
Ответ 8
В смысле скорости выполнения MySQLi выигрывает, но если у вас нет хорошей оболочки, использующей MySQLi, ее функции, касающиеся подготовленных операторов, ужасны.
У меня все еще есть ошибки, но если кто-то этого захочет, здесь.
Итак, если вы ищете ускорение скорости, то MySQLi; если вы хотите простоту использования, то PDO.
Ответ 9
Лично я использую PDO, но я думаю, что это в основном вопрос предпочтения.
У PDO есть некоторые функции, которые помогают снова SQL-инъекции (подготовленные инструкции), но если вы будете осторожны с вашим SQL, вы можете достичь этого с помощью mysqli, тоже.
Перемещение в другую базу данных не является основанием для использования PDO. Пока вы не используете "специальные функции SQL", вы можете переключиться с одной базы данных на другую. Однако, как только вы используете, например, "SELECT... LIMIT 1", вы не можете перейти на MS-SQL, где это "SELECT TOP 1...". Так что это все равно проблематично.
Ответ 10
Отредактированный ответ.
После некоторого опыта работы с обоими этими API, я бы сказал, что есть 2 уровня уровня блокировки, которые делают mysqli непригодным для использования с собственными подготовленными операторами.
Они уже упоминались в двух замечательных (но недооцененных) ответах:
(оба упомянуты в этом ответе)
По какой-то причине mysqli не удался с обоими.
В настоящее время он получил некоторое улучшение для второго (get_result), но он работает только на установках mysqlnd, означает, что вы не можете полагаться на эту функцию в ваших сценариях.
Однако он не имеет привязки по значению даже по сей день.
Итак, есть только один выбор: PDO
Все другие причины, такие как
- с именем placeholders (этот синтаксис сахара переоценен)
- поддержка различных баз данных (никто на самом деле никогда не использовал ее)
- выборка в объект (просто бесполезный синтаксический сахар)
- разница в скорости (нет)
не имеют существенного значения.
В то же время оба этих API не обладают некоторыми важными функциями , например
- идентификатор заполнителя
- заполнитель для сложных типов данных, чтобы сделать динамическое связывание менее toilsome
- более короткий код приложения.
Итак, чтобы удовлетворить потребности реальной жизни, нужно создать свою собственную библиотеку абстракции на основе одного из этих API-интерфейсов, внедряя вручную разборные заполнители. В этом случае я бы предпочел mysqli, поскольку он имеет меньший уровень абстракции.
Ответ 11
В тесте script каждый метод проверяется 10000 раз и выводится разность общего времени для каждого метода. Вы должны это сделать в своей собственной конфигурации, я уверен, что результаты будут разными!
Это мои результаты:
- "
SELECT NULL" -> PGO()
быстрее на ~ 0,35 секунды
- "
SHOW TABLE STATUS" -> mysqli()
быстрее на ~ 2,3 секунды
- "
SELECT * FROM users" -> mysqli()
быстрее на ~ 33 секунды
Примечание: используя → fetch_row() для mysqli, имена столбцов не добавляются в массив, я не нашел способ сделать это в PGO. Но даже если я использую → fetch_array(), mysqli немного медленнее, но все же быстрее, чем PGO (кроме SELECT NULL).
Ответ 12
Одна вещь, которую PDO имеет, что MySQLi не так мне нравится, - это способность PDO возвращать результат как объект определенного типа класса (например, $pdo->fetchObject('MyClass')
). MySQLi fetch_object()
возвращает только объект stdClass
.
Ответ 13
Есть одна вещь, о которой нужно помнить.
Mysqli не поддерживает функцию fetch_assoc(), которая возвращает столбцы с ключами, представляющими имена столбцов. Конечно, можно написать свою собственную функцию, чтобы сделать это, это даже не очень долго, но мне было тяжело писать действительно (для неверующих: если вам кажется легким, попробуйте ваше собственное время и не обманывайте:))