2014-02-10 16 views
2

我試圖在PHP中創建某種異步超時。使用pthreads在PHP中創建異步超時

而且我正在使用PECL擴展pthreads來完成多線程操作。

異步超時工作完美,但引用沒有。

我使用PHP 5.5.8進行此測試。

class ParentClass { 
    public $test; 

    public function __construct(){ 
    } 

    public function test() { 
     echo $this->test; 
    } 
} 

class Timeout extends Thread { 
    private $seconds; 
    private $parent; 

    public function __construct($seconds, &$parent){ 
     $this->seconds = $seconds; 
     $this->parent = $parent; 
    } 

    public function run(){ 
     sleep($this->seconds); 
     $this->parent->test(); 
    } 
} 

$parent = new ParentClass(); 
$parent->test = "Hello.\n"; 
$timeout = new Timeout(2, $parent); 
$timeout->start(); 
$parent->test = "Bye.\n"; 
$parent->test(); 

期待

Bye. 
Bye. 

獲取

Bye. 
Hello. 

有人能告訴我什麼,我做錯了什麼?

+2

我必須假設開始一個線程不會使用相同的內存對象,所以你的ParentClass實際上被複制,而不會注意到內部值的變化。文檔中有一個提示:只能存儲可序列化的值 - 這使我認爲值在執行時會被序列化。你應該var_dump父類來檢查它是否是相同的對象 – Sven

+1

@Sven好吧,所以單身是一種選擇?或者其他一些靜態類? – Sem

+0

我有想法堆棧可能是解決方案..我已經知道這是不同的對象,因爲我得到不同的回報。 http://www.php.net/manual/en/class.stackable.php – Sem

回答

7

對於多線程應用程序,不應該使用sleep(),PHP調用的底層實現是爲了讓進程進入休眠狀態,而不是進程內的線程。里程會有所不同,有些實現可能會導致線程進入睡眠狀態,但您不能也不應該依賴它。

usleep更適合於多線程,因爲它旨在使線程進入睡眠狀態,而不是進程,但是,它也使線程處於非接受狀態。

pthreads內置適當的同步方法,專爲多線程而設計,讓線程處於接受狀態,同時等待某些事情發生。

如果您希望在多個上下文之間傳遞對象進行操作,則引用不起作用,也不需要,對象應該從pthreads下降。

<?php 
define("SECOND", 1000000); 

class ParentClass extends Stackable { 

    public function test() { 
     echo $this->test; 
    } 

    public function run(){} 

    public $test; 
} 

class Timeout extends Thread { 

    public function __construct($seconds, $parent){ 
     $this->seconds = $seconds; 
     $this->parent = $parent; 
    } 

    public function run(){ 
     $this->synchronized(function(){ 
      $this->wait(
       SECOND * $this->seconds); 
     }); 
     $this->parent->test(); 
    } 

    private $seconds; 
    private $parent; 
} 

$parent = new ParentClass(); 
$parent->test = "Hello.\n"; 
$timeout = new Timeout(2, $parent); 
$timeout->start(); 
$parent->test = "Bye.\n"; 
$parent->test(); 
+0

感謝您的答案! :)我一定會在下次使用它。 – Sem