2014-02-13 4 views
1

the PHP Manual От:PHP PDO подготовил заявление в() массив

Вы не можете связать несколько значений для одного имени параметра, например, в IN() положение о операторе SQL.

Но можете ли вы использовать несколько значений, используя маркеры параметров вопросительного знака? Или у вас есть prepare() новое заявление каждый раз, когда изменяется число значений?

SELECT * FROM `table` WHERE `column` IN(?) 

Если это разрешено, как вы его заработаете?

РЕДАКТИРОВАТЬ: Два предыдущих указанных вопроса были указаны как с именами переменных, которые, по словам руководства, не могут быть связаны с несколькими параметрами. Я спрашивал о вопросительных знаках (анонимных) переменных.

+2

Это часто задают вопросы. [Здесь один] (http://stackoverflow.com/questions/920353/php-pdo-can-i-bind-an-array-to-an-in-condition) [и вот еще один] (http: // stackoverflow .com/questions/14767530/php-using-pdo-with-in-clause-array) –

+0

сделать строку из нескольких значений и связать ее –

+0

Как правило, вам нужно сделать так много??,?,?,?,? 'поскольку у вас есть элементы массива. –

ответ

1

Вот код, я взбитыми для имитации желаемого результата:

<?php 
function preprepare(&$query, &$data) { 
    preg_match_all('/\?/', $query, $matches, PREG_OFFSET_CAPTURE); 
    $num = count($matches[0]); 
    for ($i = $num; $i;) { 
     --$i; 
     if (array_key_exists($i, $data) && is_array($data[$i])) { 
      $query = substr_replace($query, implode(',', array_fill(0, count($data[$i]), '?')), $matches[0][$i][1], strlen($matches[0][$i][0])); 
      array_splice($data, $i, 1, $data[$i]); 
     } 
    } 
} 

$query = 'SELECT * FROM `table` WHERE `col1` = ? AND `col2` IN(?) AND `col3` = ? AND `col4` IN(?)'; 
$data = array('foo', array(1, 2, 3), 'bar', array(4, 2)); 
preprepare($query, $data); 
var_dump($query, $data); 
?> 

Он выводит:

array (size=2) 
    0 => string 'SELECT * FROM `table` WHERE `col1` = ? AND `col2` IN(?,?,?) AND `col3` = ? AND `col4` IN(?,?)' (length=93) 
    1 => 
    array (size=7) 
     0 => string 'foo' (length=3) 
     1 => int 1 
     2 => int 2 
     3 => int 3 
     4 => string 'bar' (length=3) 
     5 => int 4 
     6 => int 2 

Запрос и данные могут быть использованы в обычном PDO подготовил заявление. Я не знаю, учитывает ли он всю волшебную привлекательность PDO, но пока работает очень хорошо.

+0

Хотя идея совершенно правильная, но код полон волшебных и бесшумных соображений. Кроме того, вы не можете использовать * real *, чтобы подготовиться в любом случае, значит, вам все равно нужно подготовить() новый оператор каждый раз, когда число значений изменяется, поэтому цель еще не достигнута. –

+0

Однако вы двигаетесь в правильном направлении. Реализация вашего собственного заполнителя - единственное правильное решение. –

+0

Я думал, что мое решение было немного приятнее, чем другие, где вам нужно построить массив в правильном порядке. Хотя запрос должен быть «подготовлен» дважды, он работает так, как я ожидал, если он будет поддерживаться изначально. –

Смежные вопросы