2013-04-17 359 views
2

我試圖使用PHP數據庫加載一些數據,但由於某些原因,當我把它在函數內部它不工作中的數據庫。如果我嘗試了代碼,而無需一個功能,它工作正常:查詢PHP函數

//$dbc connection 
$call1 = 0; 
$output = ''; 
$query = "select * from artists order by lname limit $call1, 15"; 
$result = mysqli_query($dbc, $query); 
while($row = mysqli_fetch_array($result)){ 
    $output .= "<ul>"; 
    $output .= "<li>" . $row['name'] . "</li>"; 
    $output .= "</ul>"; 
} 

但是,當我改變的代碼是一個函數裏面,我不從數據庫中獲取任何東西(或至少它不會返回任何東西):

//$dbc connection 
$call1 = 0; 
$output = ''; 
function loadArtists($call){ 
    $query = "select * from artists order by lname limit $call, 15"; 
    $result = mysqli_query($dbc, $query); 
    while($row = mysqli_fetch_array($result)){ 
     $output .= "<ul>"; 
     $output .= "<li>" . $row['name'] . "</li>"; 
     $output .= "</ul>"; 
    } 
} 
loadArtists($call1); 

我在做什麼錯在這裏?

+0

檢查錯誤'$結果= mysq li_query($ dbc,$ query)或死('Could not connect:')。 '但是我會說這是你插入函數參數到你的SQL查詢中的方式 –

+0

如果你嘗試在函數中用'0'改變'$ call',然後在沒有參數的情況下運行函數會發生什麼,它的工作呢? –

+0

@bamwebdesign這是無關緊要的。這是連接的範圍問題。 – Kermit

回答

5

您的功能中不能使用$dbc,因爲它是一個global變量。

您可以使用

function loadArtists($call){ 
    global $dbc; 
    ... 
} 

使$dbc知道loadArtists()或者把它作爲第二個參數

function loadArtists($dbc, $call){ 
... 
} 

,並把它作爲

loadArtists($dbc, $call1); 
+4

-1 [使用'global'是不好的做法。](http://stackoverflow.com/a/5166527/679449)連接應該*傳遞給函數。 – Kermit

+1

@FreshPrinceOfSO對於「錯誤答案」不是「-1」嗎?這個答案不是「錯誤的」。所以也許應該重新考慮評論一下這是不好的做法,不要因爲你認爲不適合的東西而「-1」。你爲什麼不回答你所說的話,讓我們說爲什麼比'global'更好地使用它。 – 2013-04-17 23:12:06

+0

@Andarndar這個答案是錯誤的*,因爲它聲明OP ***「必須使用」***'全局「。 – Kermit

1

它看起來像一個範圍問題給我。您在函數中引用的$輸出與在函數外定義的$輸出不同。

您應該將功能更改爲以下:

function loadArtists($call){ 
$output = ""; 
$query = "select * from artists order by lname limit $call, 15"; 
$result = mysqli_query($dbc, $query); 
while($row = mysqli_fetch_array($result)){ 
    $output .= "<ul>"; 
    $output .= "<li>" . $row['name'] . "</li>"; 
    $output .= "</ul>"; 
} 

return $output; 

}

$輸出= loadArtists($ CALL1);

2

在同一個頁面的代碼上聲明您的用戶名和密碼,你執行你想一個數據庫連接每次都是不好的做法,因爲:

  1. 你可能有多個頁面進行編輯如果您移動到不同的主機或與開發環境不同的環境。
  2. 如果您聲明它在根之外,則可以限制從FTP帳戶訪問數據庫密碼。

我喜歡爲連接使用一個函數,所以如果連接關閉,您可以隨意重新打開它(減少服務器開銷)。此外,您不必將其設置爲函數內的全局變量(not a good idea because of several reasons)。

因此,對於這些原因,這種連接應該外面(下面)的根。

/../safe/connection.php

function openSQL() { 
    $conn = mysqli('localhost', 'my_user', 'my_password', 'my_db'); 
    return $conn; 
} 

的functions.php

require_once($_SERVER['DOCUMENT_ROOT'].'/../safe/connection.php'); 
function loadArtists($call){ 
    $dbc = openSQL(); 
    $query = "select * from artists order by lname limit $call, 15"; 
    $result = mysqli_query($dbc, $query); 
    while($row = mysqli_fetch_array($result)){ 
     $output .= "<ul>"; 
     $output .= "<li>" . $row['name'] . "</li>"; 
     $output .= "</ul>"; 
    } 
    mysqli_close($dbc); 
    return $output; 
} 

$myOutput = loadArtists(4); 
3

正如我在我的評論人提到,使用global修復的範圍您的連接is poor practice。通過你的連接的正確的方法是,像這樣:

$dbc = mysqli_connect("localhost", "my_user", "my_password", "world"); 

$call1 = 0; 
$output = ''; 
function loadArtists($call, $dbc){ 
    $query = "select * from artists order by lname limit $call, 15"; 
    $result = mysqli_query($dbc, $query); 
    while($row = mysqli_fetch_array($result)){ 
     $output .= "<ul>"; 
     $output .= "<li>" . $row['name'] . "</li>"; 
     $output .= "</ul>"; 
    } 
} 
loadArtists($call1, $dbc); 
2

問題是variable scope。該變量不存在您的功能。

有三種方式來處理是:

  1. 使它成爲全球性的,這意味着外部變量是在一個函數中readible。 (請注意,使用全局變量通常被認爲是一個安全問題。)

    global $dbc; 
    
  2. 您可以傳遞一個變量到函數作爲參數

    function loadArtists($connection, $call) { ... } 
    
  3. 你可以做一個類和類變量現在的類函數內部可用:

    class Artists { 
        public $dbc; 
        public function __construct() { 
         $this->dbc = open_the_db_connection(); //etc? 
        } 
        public function loadArtists($call) { 
         $query = "select * from artists order by lname limit $call, 15"; 
         $result = mysqli_query($this->dbc, $query); 
         while($row = mysqli_fetch_array($result)){ 
          $output .= "<ul>"; 
          $output .= "<li>" . $row['name'] . "</li>"; 
          $output .= "</ul>"; 
         } 
         return $output; 
        } 
    }