2011-06-09 74 views
5

我對OOP風格的PHP很新,我也試圖實現PDO。我在網上發現了這個可以處理數據庫連接的小班,但是我不知道如何從另一個班級訪問它。下面是代碼:PHP和PDO類問題

class PDO_DBConnect { 
    static $db ; 
    private $dbh ; 
    private function PDO_DBConnect() { 
     $db_type = 'mysql'; //ex) mysql, postgresql, oracle 
     $db_name = 'postGal'; 
     $user = 'user' ; 
     $password = 'pass' ; 
     $host = 'localhost' ; 
     try { 
      $dsn = "$db_type:host=$host;dbname=$db_name"; 
      $this->dbh = new PDO ($dsn, $user, $password); 
      $this->dbh->setAttribute(PDO::ATTR_PERSISTENT, true); 
      $this->dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); 
     } catch (PDOException $e) { 
      print "Error!: " . $e->getMessage() . "\n" ; 
      die() ; 
     } 
    } 

    public static function getInstance () { 
     if (! isset (PDO_DBConnect::$db)) { 
      PDO_DBConnect::$db = new PDO_DBConnect () ; 
     } 
     return PDO_DBConnect::$db->dbh; 
    } 
    } 

    $db_handle = PDO_DBConnect::getInstance(); 

    class Person 
    { 
    function __construct() 
    { 
     $STMT = $db_handle->prepare("SELECT title FROM posts WHERE id = ? AND author = ? LIMIT 20"); 
     $STMT->execute(array('24', 'Michael')); 

     while ($result = $STMT->fetchObject()) 
     { 
     echo $result->title; 
     echo "<br />"; 
     } 
    } 
    } 

我怎樣才能得到我的Person類的內部訪問$db_handle變量?我是否必須實例化Person類中的變量?如果是這樣,這是否意味着我將永遠不得不稱之爲$this->db_handle?我希望避免這種情況。 (我仍然只有具有可變範圍的帶班一個非常基本的理解)

+0

爲什麼你使用PHP5 OO構造,但PHP4時代的同名類構造函數?請考慮切換到'__construct'。 – Charles 2011-06-09 19:06:40

+0

我不認爲他寫了PDO_DBConnect類,因爲他提到他「找到了」。 – Problematic 2011-06-09 19:11:43

回答

5

有(至少)三種方法來處理這個問題。最便攜的,並推薦稱爲「依賴注入」,通過它的__construct()將數據庫句柄傳遞到您的類,並將其存儲在類變量中。需要像$this->db那樣訪問它,就像你不想做的那樣。

class Person { 
    // Member to hold the db handle 
    public $db; 

    public function __construct($db_handle) { 
    // Assign the handle to a class member variable in the constructor 
    $this->db = $db_handle; 
    } 
    public function otherFunc() { 
    $this->db; // do something 
    } 
} 

$person = new Person($db_handle); 

下一頁的方法是實例化的構造內的$db_handle而不是將它英寸這是有點難以測試和調試。

class Person { 
    public $db; 
    public function __construct() { 
     $this->db = PDO_DBConnect::getInstance(); 
    } 
} 

最後,你可以調用$db_handle作爲global每當你在課堂上使用它。這可能是最難讀懂和調試的。

class Person { 
    public function __construct() { 
    global $db_handle; 
    } 
    public function otherFunc() { 
    global $db_handle; 
    $db_handle; // do something 
    } 
} 
+0

非常感謝您對此進行闡述。正是我需要知道的。我認爲構建方法對於我想要使用它的最有意義。謝謝! – 2011-06-09 19:22:23

+0

只是真正困惑什麼是被調用的,什麼時候是因爲該類與它內部的函數具有相同的名稱。這完成了什麼? – 2011-06-09 19:26:29

+0

@Eujung Kim哪個類與其中的函數名稱相同? – 2011-06-09 19:57:30

3

你應該使用Dependency Injection

$steve = new Person($db_handle); 

是的,用你希望避免的語法是做它的方式。你總是可以通過說$dbh = $this->db_handle;將類變量分配給一個本地方法,我相信它的速度稍快。

3

如果你真的從Person對象中必須做數據庫的工作(separation of concerns說,這應該被照顧的其他地方),你可以把它作爲一個構造函數的參數(根據您的使用情況,它看起來像可能是你想要的方式),或者作爲二傳手注射。對於前者:

class Person 
{ 
    function __construct($db_handle) 
    { 
     // ... your existing code 

然後你實例化對象的人,像這樣:

$person = new Person($db_handle); 

這真的是你能避免需要使用$this->db_handler而不復制變量爲局部範圍的唯一途徑。