MySQL подготовил оператор против обычного запроса. Прибыль и убытки

Я в середине обновления / переделки кода базы данных, и мне было интересно, чего я должен ожидать от использования подготовленных операторов.

Возьмите этот пример кода:
(голый со мной, я знаю, что это уродливо – я это написал)

$values = ''; for ($i = 0; $i < $count; $i++) { $name = mysql_real_escape_string ($list[$i][1]); $voc = mysql_real_escape_string ($list[$i][3]); $lev = $list[$it][2]; $lev = is_numeric ($lev)? $lev : 0; $values .= ($values == '')? "('$name', '$voc', $lev)" : ", ('$name', '$voc', $lev)"; } if ($values != '') { $core->query ("INSERT INTO onlineCList (name, voc, lev) VALUES $values;"); } 

Теперь, несмотря на очевидный выигрыш в удобочитаемости (, здравомыслие) и тот факт, что max_packet_size перестает быть проблемой, я должен ожидать каких-либо изменений в производительности, когда я перекодирую это для использования подготовленных операторов? Я подключаюсь удаленно к серверу MySQL, и я беспокоюсь, что отправка нескольких небольших пакетов будет значительно медленнее, чем отправка одного большого пакета. Если это так, может ли MySQLi / mysqlnd кэшировать эти пакеты?

Другой пример:

 $names = ''; while ($row = mysql_fetch_array ($result, MYSQL_ASSOC)) { $name = mysql_real_escape_string($row['name']); $names .= ($names == '') ? "'$name'" : ", '$name'"; } if ($names != '') { $core->query ("UPDATE onlineActivity SET online = NULL WHERE name IN ($names) AND online = 1;"); } 

Как и выше, следует ли ожидать неожиданного, перекодируя это, чтобы использовать подготовленные заявления? Разве это имеет значение для сервера MySQL, если он должен запускать один запрос с большим предложением IN или несколькими подготовленными запросами с проверками равенства ( .. WHERE name = $name AND .. )?

Предположим, что все правильно проиндексировано.

    Обычно, если вы просто используете подготовленный оператор вместо простого запроса, он немного медленнее, так как запрос готов и выполняется в два шага вместо одного. Подготовленные утверждения становятся быстрее только тогда, когда вы готовите инструкцию, а затем выполняете ее несколько раз.

    Однако в этом случае вы используете mysql_real_escape_string , который выполняет mysql_real_escape_string в базу данных. Хуже того, вы делаете это внутри цикла, поэтому выполняете его несколько раз за запрос . Таким образом, в этом случае замена всех этих roundtrips одним подготовленным заявлением является беспроигрышной.

    Что касается вашего последнего вопроса, нет причин, по которым вы не можете использовать один и тот же запрос с подготовленным оператором, как и с обычным парсером запросов (т. Е. Нет причин для выполнения одной версии с IN, а другая с группой OR). Подготовленный оператор может иметь IN (?, ?, ?) , А затем вы просто связываете это количество параметров.

    Мой совет – всегда использовать подготовленные заявления. В тех случаях, когда они добавляют предельные эксплуатационные издержки, они по-прежнему стоят за безопасность (без внедрения SQL) и преимущества чтения. Конечно, в любое время, когда вы прибегаете к mysql_real_escape_string , mysql_real_escape_string этого вы должны использовать подготовленный оператор. (Для простых одноразовых запросов, в которых нет необходимости избегать ввода переменных, они не являются абсолютно необходимыми.)

    1. Подготовленные заявления более безопасны.
    2. Подготовленные заявления имеют лучшую производительность.
    3. Подготовленные утверждения удобнее писать.

    Вы прочитаете все это!

    http://dev.mysql.com/tech-resources/articles/4.1/prepared-statements.html

    попробуйте это тоже

    Подготовленное заявление против хранимой процедуры