2016-04-29 105 views
3

我在php中使用PDO。但是,當我的查詢有任何關鍵字像「'」意味着連字符它打破並通過一個錯誤。 我準備通過互聯網,並找到解決方案綁定與查詢參數,它工作正常。 但問題是我在循環中構建查詢,我無法在循環內綁定參數。 這是代碼,我用空間拆分數組,並對每個關鍵字運行查詢。 前3個單詞將只有像查詢和更多然後3個單詞我正在使用循環來連接所有數組元素和相同的多於6個單詞我正在使用MATCH查詢。 有沒有什麼辦法來逃避這個連字符,或者我們如何在我的情況下使用循環綁定參數?在PHP中使用PDO綁定參數

 $keyword = ($_POST['keyword']); 
     $keyword_array = split(' ',$keyword); 

     /* Query For first Three Words */ 
     if(count($keyword_array)<=3){ 
        $sql = "SELECT * FROM faq WHERE question LIKE '%$keyword%' limit 14"; 
     } 
     /* Query through all array when words are greater then 3 */ 
     if(count($keyword_array)< 6){ 
      $sql = "SELECT * FROM faq WHERE question "; 
       for($i = 0 ; $i<count($keyword_array); $i++){ 

       if($i==0){ 
           $sql.=" LIKE '%$keyword_array[$i]%'"; 
       }else{ 
           $sql.=" or question LIKE '%$keyword_array[$i]%' "; 
       } 
      } 
         $sql .= " ORDER BY question ASC LIMIT 0, 8"; 
     } 
     /* Appl FULL TEXT in natual language mode once we have enough phrase */ 
     else if(count($keyword_array)>=6){ 
       $sql = "SELECT * FROM faq WHERE "; 
        for($i = 0 ; $i<count($keyword_array); $i++){ 

        if($i==0){ 
            $sql.=" MATCH (answer) AGAINST ('$keyword_array[$i]' in natural language mode) "; 
        }else{ 
            $sql.=" or MATCH(answer) AGAINST('$keyword_array[$i]' in natural language mode) "; 
        } 
      } 
       $sql .= " limit 0,5"; 
     } 


      $execute_faq_query = $conn->query($sql); 
      $execute_faq_query->setFetchMode(PDO::FETCH_ASSOC); 

      while ($list = $execute_faq_query->fetch()){ 
} 
+0

循環應構建SQL語句,然後執行單個SQL查詢。 –

+0

是的,我確實嘗試過,但我有問題,因爲我是新的PDO,你可以請任何循環的幫助,然後我會用在所有其他。 – Bilal

+0

PDO支持像':keyword'這樣的命名佔位符,然後您可以在'execute(array(':keyword'=> $ keyword))''中引用''。把東西添加到字符串很容易,如果你同時向你的數組添加東西,它們將保持同步。 – tadman

回答

2

構建動態查詢時,需要將查詢中那些靜態的部分與動態的部分分開。

你可以看到下面的代碼是靜態的。

"SELECT * FROM faq "; 

其餘的代碼是動態的。過濾記錄時,使用WHERE子句,並使用AND運算符來根據多個條件過濾記錄。如果第一個條件和第二個條件都爲真,則AND運算符顯示記錄。如果第一個條件或第二個條件爲真,則OR運算符顯示記錄。所以在使用,但之後AND或OR必須使用的第一個條件(使用或在您的例子)

// Static code 
sql = "SELECT * FROM `faq`" 
// Set initial condition to WHERE  
clause = "WHERE";  
if(!empty(filter)){ 
    Add clause to sql 
    Add condition to sql 
    change clause to OR or AND as required 
} 

重複每個過濾器 注意過濾器不改變,直到應用濾鏡和保持改變一旦改變。 在處理完所有過濾器後,添加剩餘的靜態代碼(如果有)。

我已經使用Switch Case來應用濾波器和未命名的參數嗎?

儘可能使用「懶惰」綁定 - 將數據傳遞到執行會顯着縮短您的代碼。見PDO info

//Test $POST[] remove after testing 
$_POST['keyword'] ="one two three four five six"; 
$keyword = ($_POST['keyword']); 
$keyword_array = split(' ',$keyword); 
$words = count($keyword_array); 
echo $words; 
//You need an array to store parameters 
$paramArray =array(); 
//Initial clause 
$clause = "WHERE"; 
//Start with a basic stub 
$sql = "SELECT * FROM faq "; 
switch (true) { 
    case $words <= 3: 
     $sql .= " $clause question LIKE ?"; 
     $keyword = "%$keyword%"; 
     array_push($paramArray,$keyword); 
     $limit = " LIMIT 14"; 
     break; 

    case $words < 6: 
     for($i = 0 ; $i<count($keyword_array); $i++){ 
      $sql .= " $clause question LIKE ?"; 
      $keyword = "%$keyword_array[$i]%"; 
      array_push($paramArray,$keyword); 
      $clause = "OR"; 
      $limit = " ORDER BY question ASC LIMIT 0, 8"; 
     } 
     break; 

    case $words >=6: 
     $clause = ""; 
     for($i = 0 ; $i<count($keyword_array); $i++){ 
      $sql.=" $clause MATCH (answer) AGAINST (? in natural language mode) "; 
      array_push($paramArray,$keyword_array[$i]); 
      $clause = "OR"; 
      $limit = " limit 0,5"; 
     } 
     break; 
} 
//echo query and parameter array remove after testing 
echo $sql; 
echo "<br>"; 
print_r($paramArray); 

//Prepare and execute query 
$execute_faq_query = $conn->prepare($sql); 
$execute_faq_query->execute($paramArray); 
$execute_faq_query->setFetchMode(PDO::FETCH_ASSOC); 
while ($list = $execute_faq_query->fetch()){ 
} 
+0

「儘可能使用」懶惰「綁定」是! – miken32

+0

這正是我一直在尋找的。 – Bilal