如何在php中跨线程共享全局变量?

发布时间:2022-04-30 发布网站:脚本宝典
脚本宝典收集整理的这篇文章主要介绍了如何在php中跨线程共享全局变量?脚本宝典觉得挺不错的,现在分享给大家,也给大家做个参考。
在多线程中,全局变量或资在线程之间共享.
我在c中使用pthread

#include <stdio.h>
#include <pthread.h>
#include <unistd.h>

void *worker(void *);

int ctr = 0;
pthread_mutex_t lock;

int main(int argc,char *argv[])
{
  pthread_t t[2];
  int i = 0;

//~ pthread_mutex_inIT(&amp;lock,NULL);

  while(i < 2)
  {
     pthread_create(&t[i],NULL,&worker,NULL);
     i++;
  }

  pthread_join(t[0],NULL);
  pthread_join(t[1],NULL);

//~ pthread_mutex_destroy(&lock);
//~ pthread_join(t[1],NULL);
  return 0;
}

void *worker(void *arg)
{
//~ pthread_mutex_lock(&lock);
//~ int ctr = 0;
    ctr += 1;

    PRintf("job %d started\n",ctr);
    sleep(1);
//~ ctr += 1;
    printf("job %d finished\n",ctr);

//~ pthread_mutex_unlock(&lock);
}

代码输出

job 1 started
job 2 started
job 2 finished
job 2 finished

在此代码中,变量ctr在线程之间共享,因此其他线程对该变量所做的更改对另一个线程是可见的(除非完成对某些互斥锁的调用).

我在PHP中试过但没有运气(使用PHP pthreads).
这是我的PHP代码

global $ctr;

Class WorkerThread extends Worker
{
    private $thread_id;
    //~ public static $ctr = 0;
    private $mutext;

public function WorkerThread($mutex = NULL)
{ 
    //~ $this->ctr = $ctr;
    $this->;mutex = $mutex;
    $this->start();
}

public function run()
{
    //~ Mutex::lock($this->mutex);
    $new_line = PHP_sapi_name() == "cli" ? PHP_EOL : "<br>";
    //~ global $ctr;
    $ctr = 0;
    $ctr += 1;
    echo "Thread " . $ctr . " started" . " [ " . $this->getThreadId() . " ]" . $new_line;
    sleep(1);
    echo "Thread " . $ctr . " Finished" . " [ " . $this->getThreadId() . " ]" . $new_line;
    //~ var_dump($this);
    //~ Mutex::unlock($this->mutex);
 }
}

//~ $mutex = Mutex::create();
$i = 0;
$worker = array();

while($i < 2)
{
   $worker[$i] = new WorkerThread();
//~ $worker[$i]->start();
   $i++;
}

foreach(range(0,1) as $t)
   $worker[$t]->join();

//~ Mutex::destroy($mutex);

输出代码

Thread 1 started [ -1257948352 ]
Thread 1 started [ -1267893440 ]
Thread 1 Finished [ -1257948352 ]
Thread 1 Finished [ -1267893440 ]

变量ctr(全局)没有像上面的c代码一样被线程更新?

何在PHP(跨线程共享资源)中做到一点

解决方法

通常,线程在与启动它们的进程相同的地址空间中执行.

因此,在C中,新线程能够直接访问主程序堆栈上的变量.

PHP中创建新线程时,它有一个单独的堆,它必须在单独的地址空间中执行.

这意味着认情况下,您无法在线程之间共享全局状态.

这是PHP正常线程模型 – 无共享.

pthreads所做的是引入能够在许多上下文中操作的对象,并且能够在这些上下文之间共享数据.

等效的PHP代码可能类似于:

<?PHP
class Atomic extends Threaded {

    public function __construct($value = 0) {
        $this->value = $value;
    }

    public function inc() {
        return $this->value++;
    }

    /* ... */
    private $value;
}

class test extends Thread {

    public function __construct(Atomic $atomic) {
        $this->atomic = $atomic;
    }

    public function run() {
        $this->atomic->inc();
    }

    private $atomic;
}

$atomic = new Atomic();
$threads = [];

for ($thread = 0; $thread < 2; $thread++) {
    $threads[$thread] = new Test($atomic);
    $threads[$thread]->start();
}

foreach ($threads as $thread)
    $thread->join();

VAR_dump($atomic);
?>

请注意,Mutex不是直接使用的(并且已从最新版本的pthread中删除).使用Mutex是危险的,因为您没有足够的执行控制来安全地使用它们;如果您锁定互斥锁然后由于某种原因解释器遭受致命错误,您将无法释放互斥锁,死锁将跟随…

也没有必要,因为对象范围上的单个指令操作是原子的.

在实现排除时,您可以使用Threaded :: synchronized API获得很好的效果.

如果需要排除,run方法可能看起来更像:

public function run() {
        $this->atomic->synchronized(function($atomic){
            /* exclusive */
            $atomic->inc();
        },$this->atomic);
    }

最后,给命名事项的一课…

你似乎是,并且被认为是在posix线程(标准,pthread)和pthreads之间有一些平行,PHP扩展…

pthreads,PHP扩展恰好使用Posix Threads,但它没有实现像Posix Threads这样的东西.

pthreads这个名字应该被理解为PHP线程…命名很难.

脚本宝典总结

以上是脚本宝典为你收集整理的如何在php中跨线程共享全局变量?全部内容,希望文章能够帮你解决如何在php中跨线程共享全局变量?所遇到的问题。

如果觉得脚本宝典网站内容还不错,欢迎将脚本宝典推荐好友。

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
如您有任何意见或建议可联系处理。小编QQ:384754419,请注明来意。