2010-09-15 16 views
7

z http://www.php.net/manual/en/class.pdo.phpSingleton PHP PDO

###### config.ini ###### 
db_driver=mysql 
db_user=root 
db_password=924892xp 

[dsn] 
host=localhost 
port=3306 
dbname=localhost 

[db_options] 
PDO::MYSQL_ATTR_INIT_COMMAND=set names utf8 

[db_attributes] 
ATTR_ERRMODE=ERRMODE_EXCEPTION 
############ 

<?php class Database { 
    private static $link = null ; 

    private static function getLink () { 
     if (self :: $link) { 
      return self :: $link ; 
     } 

     $ini = _BASE_DIR . "config.ini" ; 
     $parse = parse_ini_file ($ini , true) ; 

     $driver = $parse [ "db_driver" ] ; 
     $dsn = "${driver}:" ; 
     $user = $parse [ "db_user" ] ; 
     $password = $parse [ "db_password" ] ; 
     $options = $parse [ "db_options" ] ; 
     $attributes = $parse [ "db_attributes" ] ; 

     foreach ($parse [ "dsn" ] as $k => $v) { 
      $dsn .= "${k}=${v};" ; 
     } 

     self :: $link = new PDO ($dsn, $user, $password, $options) ; 

     foreach ($attributes as $k => $v) { 
      self :: $link -> setAttribute (constant ("PDO::{$k}") 
       , constant ("PDO::{$v}")) ; 
     } 

     return self :: $link ; 
    } 

    public static function __callStatic ($name, $args) { 
     $callback = array (self :: getLink (), $name) ; 
     return call_user_func_array ($callback , $args) ; 
    } 
} ?> 

<?php // examples 
$stmt = Database :: prepare ("SELECT 'something' ;") ; 
$stmt -> execute () ; 
var_dump ($stmt -> fetchAll ()) ; 
$stmt -> closeCursor () ; 
?> 

moje pytania są następujące:

Co jest Singleton?

Co oznacza błąd statyczny/nie?

Co jest publiczna funkcja statycznego __callStatic (służy?

A jak mogę to zrobić, że PDO łączy się tylko do bazy danych, gdy są potrzebne? Takie jak kwerendy lub ucieczki? Więc jeśli klasa/przedmiot jest nieużywany to się nie łączy

+2

Singletons zostały poddane dużo krytyki na przestrzeni lat i należy ich unikać, jeśli to możliwe. Jest to szczególnie ważne w środowiskach, w których wszystkie obiekty działają tylko dla żądania. Rozejrzyj się po SO, aby uzyskać więcej informacji. – Gordon

+0

@gordon: Singletony nie są (!) Złym rozwiązaniem w ogóle. Są one bardzo użyteczne na przykład dla front-kontrolerów, obiektów-żądań itd. Ale również uważam, że nie jest to zalecane do używania z obiektami bazy danych. Ale nie możesz powiedzieć "po prostu ich unikaj", tak myślę. Jest to powszechny wzorzec projektowy i bardzo przydatny. –

+1

@faileN Singletons są (!) Ogólnie złym rozwiązaniem. Nawet [Erich Gamma mówi to w dzisiejszych czasach] (http://www.informit.com/articles/printerfriendly.aspx?p=1404056). Nie będę się w to zagłębiał, ponieważ zostało to wystarczająco wyjaśnione w innym miejscu. Tak jak powiedziałem, [rozejrzyj się] (http://stackoverflow.com/search?q=singleton+php) – Gordon

Odpowiedz

4

Singleton to wzorzec projektowania oprogramowania, który ogranicza inicjowanie klasy do jednej instancji. http://en.wikipedia.org/wiki/Singleton_pattern

Statyczny oznacza, że ​​coś należy do klasy, a nie do konkretnej instancji. W PHP oznacza to również, że należy wywołać metodę statyczną z :: nie ->

_callStatic zwraca link PDO, jeśli został już ustanowiony. W przeciwnym razie najpierw tworzy link, a następnie go zwraca.

Odpowiedź na czwarte pytanie dotyczy właśnie wzoru singleton. Gwarantuje to, że połączenie zostanie skonfigurowane tylko raz, w razie potrzeby.

+0

A * możliwe * odpowiedź na czwarte pytanie dotyczy użycia wzoru singleton. Istnieją inne sposoby (na przykład łączenie leniwie). – strager

+0

Dlaczego __callStatic potrzebujesz call_user_func_array? – Johnny

+0

@Johnny, To '__callStatic' działa jako proxy dla' self :: getLink() -> name'. Kiedy wywołujesz 'Database :: query', jest ono tłumaczone na' Database :: getLink() -> query'. – strager

0

Singleton oznacza, że ​​masz tę klasę, która będzie miała tylko jeden obiekt z nią związany, więc ta klasa będzie tylko utworzona tylko jeden raz, po tym czasie wywołasz metodę z nazwa taka jak getInstance(), która zwróci twoją instancję.

Statyczna, oznacza, że ​​dostęp do tego method lub property nie trzeba i wystąpienie tego obiektu, można nazwać method bezpośrednio ze swojej klasie class::myMethod()

__callStatic jest sposób można uzyskać dostęp do tych metody statycznej. Jest jednym z PHPmagic-methods i jest podobny do __call z tą różnicą, o której właśnie wspomniałem.

Dla ostatniego pytania, klasa ta otrzymuje tylko jedno połączenie z bazą danych. Jeśli dodać innej metody na przykład executeSelect($sql) trzeba będzie coś takiego:

public static function executeSelect($sql) 
{ 
    if (self::$link) 
    { 
      self::getLink() 
    } 
     // execute your query here... 
    return null; 
} 

będzie trzeba tylko zadzwonić podoba: Database::executeSelect($sql); i nigdy nie dostanie dwa połączenia z DB jednocześnie.

0

Singleton jest obiektem, który zapewnia, że ​​tylko jedna instancja jest aktywna jednocześnie. Oznacza to, że możesz zrobić tylko jedną na program, jeśli wiesz o co mi chodzi.

Metoda statyczna to taka, która może być wywołana jak normalna funkcja, poza kontekstem obiektu. Podobnie jak SomeClass:afunc() i nie tylko $this->afunc().

3

Jedna tona to funkcja statyczna, która pozwala śledzić instancje obiektów, gdy używa się pojedynczego wystąpienia obiektu, ale wystąpienia zawsze pozostają z powiązanym obiektem.

Weźmy ten przykład:

$db1 = new Database(); 
$db2 = new Database(); 

jak widać, że db1 i db2 są 2 nowe instancje bazy danych więc nie to samo, teraz podjąć ten przykład.

$db1 = Database::Instance(); 
$db2 = Database::Instance(); 

I kod na przykład

class Database 
{ 
    private static $_instance; 

    public static Instance() 
    { 
     if(self::$_instance !== null) 
     { 
      //We have already stored the object locally so just return it. 
      //This is how the object always stays the same 
      return self::$_instance; 
     } 
     return self::$_instance = new Database(); //Set the instance. 
    } 
} 

Jeśli analizować kod będzie tak, że bez względu na to gdzie użyć instancji całej aplikacji Twój obiekt zawsze będzie taka sama.

Funkcja statyczna jest metodą wewnątrz klasy/obiektu isa typu metody, która może być używana bez inicjalizowanego obiektu.

Jeśli chodzi o metodę __callStatic, jest to metoda magiczna, która jest wykonywana, gdy metoda statyczna nie jest dostępna.

Na przykład:

class Database 
{ 

    public static function first() 
    { 
     echo 'I actually exists and I am first'; 
    } 

    public function __callStatic($name,$args) 
    { 
     echo 'I am '. $name .' and I was called with ' . count($args) . ' args'; 
    } 
} 

pozwala je przetestować.

Database::first(); //Output: I actually exists and I am first 

Database::second(); //Output: I am second and I was called with 0 args 

Database::StackOverflow(true,false); //Output: I am StackOverflow and I was called with 2 args 

Nadzieja to pomaga

+0

Dzięki: Dlaczego __callStatic używa call_user_func_array? – Johnny

+0

'call_user_func_array' jest funkcją używaną do wywołania mathod lub funkcji, a przykład użycia jest podobny do' call_user_func_array ('Database :: Stack', array ('Overflow')) 'czarownica wywołałaby statyczną funkcję w bazie danych o nazwie Stack i przekazać 1 argument, głównie używam tego w MVC Patterns and Routers. – RobertPitt