2011-01-26 23 views
5

onun yapıcı içerisinde nesne oluşturma önlemek için bir yol var mı Breaking böylece:, yapıcı

$object = new Foo(); 
echo $object; // outputs: NULL 
+0

[PHP yapıcısı bir NULL döndürmek için olası kopyası.] (Http://stackoverflow.com/questions/2214724/php-constructor-to-return-a-null) –

cevap

13

Hayır, mümkün değildir;anahtar kelimesi her zaman, kurucudan ne döndürme girişiminde bulunursanız olun, belirtilen sınıfın bir örneğini döndürür. Bunun nedeni, kurucunuzun çağrıldığı andan beri PHP'nin yeni nesne için bellek ayırmayı çoktan bitirmiş olmasıdır. Başka bir deyişle, nesne bu noktada zaten var (aksi takdirde, kurucuyu arayacak hiçbir nesne yoktur).

Hatalar oluşturabilir veya bunun yerine kurucudan istisnalar atabilir ve bunlara uygun şekilde işlem yapabilirsiniz.

class Foo { 
    public function __construct() { 
     throw new Exception('Could not finish constructing'); 
    } 
} 

try { 
    $object = new Foo(); 
} catch (Exception $e) { 
    echo $e->getMessage(); 
} 
+3

@Gordon: Evet, yanlış anladım, teşekkürler; Örneği gerçekte yaratan "yeni" anahtar kelimedir; Varsa PHP'nin '__construct() işlevini çağırdığı bu nesnenin tahsisi sırasında. – BoltClock

2

Basitçe bir istisna:

throw new Exception('thou shalt not be born!'); 
+0

Bu, nesnenin yarattı. –

+0

Ahah! Komik olmak için +1! – Tivie

1

Nesne oluşturmayı sizin için yapacak bir fabrika uygulayabilirsiniz. Eğer PHP 5.3.0+ kullanıyorsanız, bunu kolaylaştıran Late Static Binding adlı bir özelliğe erişebileceksiniz.

<?php 
class MyObject 
{ 
    protected $loadSuccess = false; 

    protected function __construct ($foo, $bar, $baz) 
    { 
     // Just a random 50/50 success probability. Put real logic for testing success here 
     $this -> loadSuccess = (mt_rand (0, 99) > 49); 
    } 

    static public function factory ($foo, $bar, $baz) 
    { 
     $objClass = get_called_class(); 
     $obj = new $objClass ($foo, $bar, $baz); 
     if ($obj -> loadSuccess) 
     { 
      return ($obj); 
     } 
    } 
} 

class MySubClass extends MyObject 
{ 
    protected function __construct ($foo, $bar, $baz) 
    { 
     parent::__construct ($foo, $bar, $baz); 
     if ($this -> loadSuccess) 
     { 
      echo ('Hello, I\'m a ' . get_called_class() . '<br>'); 
     } 
    } 
} 

class MySubSubClass extends MySubClass 
{ 
    protected function __construct ($foo, $bar, $baz) 
    { 
     parent::__construct ($foo, $bar, $baz); 
     if ($this -> loadSuccess) 
     { 
      echo ($foo * $bar * $baz . '<br>'); 
     } 
    } 
} 

$o1 = MyObject::factory (1, 2, 3); // Base class 
$o2 = MySubClass::factory (4, 5, 6); // Child class 
$o3 = MySubSubClass::factory(7, 8, 9); // Descendent class 

var_dump ($o1); 
var_dump ($o2); 
var_dump ($o3); 
?> 

PHP bir sürümünü kullanıyorsanız önce 5.3.0 sonra işler geç statik bağlama ve get_called_class olarak biraz daha karmaşık olsun() kullanılamaz. Ancak, PHP 5 yansımayı destekliyor ve onu geç statik bağlama taklit etmek için kullanabilirsiniz. Alternatif olarak, ayrı bir fabrika sınıfı uygulayabilir ve bunu, ne tür bir nesneyi başlatmak istediğinizi belirten bir argüman iletebilirsiniz.

Başka bir yaklaşım, yapıcınızın başarısız olması ve bir yakalama bloğu ile işlenmesi durumunda bir istisna atmasını sağlamaktır. Bununla birlikte, eğer bu yöntem çok fazla yapıyorsanız ve bu sadece normalde nesne yaratmanın başarılı olmasını beklediğinizde kullanılmalıdır (başka bir deyişle, yaratma hatası istisnai bir durumsa).

Fabrika yaklaşımının ek avantajları vardır, örneğin önceden oluşturduğunuz nesnelerin bir önbelleğini tutabilir ve aynı nesneyi iki kez oluşturmaya çalışırsanız, bunun yerine yalnızca bir başlatılan nesneyi referans olarak geçirirsiniz yeni bir tane oluşturmak. Bu, bellek oluşturma ve özellikle nesne oluşturma, karmaşık bir SQL sorgusu gibi karmaşık bir SQL sorgusu

0

bir nesneyi gerektiriyorsa, bir nesneyi birkaç koşula bağlı olarak bir örneklemeyi durdurmaya çalışırsanız, neden yaratmaz PHP new’u bile kullanmadan önce bir durum ve sınıfı başlatabilir misiniz? Demek istediğim

, sizin örnekte ki:

$object = new Foo(); 
echo $object; // outputs: NULL 

sizin için doğrulama çalışır ya da sadece basit bir deyimi eğer sadece edecek bir kez sınıf örneğini eğer bir fonksiyon içine olabilir . Bunun gibi

:

if(conditions_to_meet){ 
    $object = new Foo(); 
} 
else $object = NULL; 

ardından da söz konusu birden çok kez örneğini bir fonksiyon içine ve sınıfına parametreler geçirmeniz gerekiyorsa

.

Bu yardımcı olur umarım.