PHP协程实现原理与开发实战协程是用户态的轻量级线程。PHP的协程由Swoole扩展提供支持也可以在PHP层面使用生成器模拟。协程适合IO密集型场景可以在不增加线程的情况下处理大量并发。生成器实现的简易协程调度器phpclass Task{private Generator $coroutine;private string $taskId;private bool $finished false;public function __construct(string $taskId, Generator $coroutine){$this-taskId $taskId;$this-coroutine $coroutine;}public function run(): void{if ($this-finished) return;if ($this-coroutine-valid()) {$this-coroutine-send(null);} else {$this-finished true;echo 任务 {$this-taskId} 完成\n;}}public function isFinished(): bool{return $this-finished || !$this-coroutine-valid();}public function getTaskId(): string{return $this-taskId;}}class Scheduler{private SplQueue $tasks;public function __construct(){$this-tasks new SplQueue();}public function add(Task $task): void{$this-tasks-enqueue($task);}public function run(): void{while (!$this-tasks-isEmpty()) {$task $this-tasks-dequeue();$task-run();if (!$task-isFinished()) {$this-tasks-enqueue($task);}}}}// 模拟IO操作function ioOperation(string $name, int $ms): Generator{echo {$name}: 开始 ({$ms}ms)\n;yield; // 模拟异步等待echo {$name}: 完成\n;}$scheduler new Scheduler();$scheduler-add(new Task(A, ioOperation(请求API1, 2000)));$scheduler-add(new Task(B, ioOperation(请求API2, 1000)));$scheduler-add(new Task(C, ioOperation(请求API3, 1500)));$start microtime(true);$scheduler-run();echo 总耗时: . round((microtime(true) - $start) * 1000) . ms\n;?Swoole协程的使用方式php// Swoole协程use function Swoole\Coroutine\go;use function Swoole\Coroutine\run;function httpGet(string $url): string{$cli new Swoole\Coroutine\Http\Client(parse_url($url, PHP_URL_HOST), 80);$cli-get(parse_url($url, PHP_URL_PATH));return $cli-body;}function mysqlQuery(string $sql): array{$swoole_mysql new Swoole\Coroutine\MySQL();$swoole_mysql-connect([host 127.0.0.1,port 3306,user root,password ,database test,]);return $swoole_mysql-query($sql);}run(function () {// 并发执行多个HTTP请求$results [];go(function () use ($results) {$results[api1] httpGet(http://api.example.com/data1);});go(function () use ($results) {$results[api2] httpGet(http://api.example.com/data2);});go(function () use ($results) {$results[users] mysqlQuery(SELECT * FROM users LIMIT 10);});// 等待所有协程完成echo 所有请求完成\n;});?协程通道用于协程间通信phpuse Swoole\Coroutine\Channel;use function Swoole\Coroutine\go;use function Swoole\Coroutine\run;run(function () {$channel new Channel(10);// 生产者协程go(function () use ($channel) {for ($i 1; $i 10; $i) {$channel-push(数据{$i});echo 生产: 数据{$i}\n;}$channel-close();});// 消费者协程go(function () use ($channel) {while (true) {$data $channel-pop();if ($data false) break;echo 消费: {$data}\n;}});});?协程和普通函数的区别是协程可以暂停和恢复执行。在IO操作时协程自动让出CPU等IO完成后再恢复执行。这让单进程可以处理大量并发连接而不需要创建大量线程。理解协程的原理能更好地利用Swoole等高性能框架的能力。
PHP协程实现原理与开发实战
PHP协程实现原理与开发实战协程是用户态的轻量级线程。PHP的协程由Swoole扩展提供支持也可以在PHP层面使用生成器模拟。协程适合IO密集型场景可以在不增加线程的情况下处理大量并发。生成器实现的简易协程调度器phpclass Task{private Generator $coroutine;private string $taskId;private bool $finished false;public function __construct(string $taskId, Generator $coroutine){$this-taskId $taskId;$this-coroutine $coroutine;}public function run(): void{if ($this-finished) return;if ($this-coroutine-valid()) {$this-coroutine-send(null);} else {$this-finished true;echo 任务 {$this-taskId} 完成\n;}}public function isFinished(): bool{return $this-finished || !$this-coroutine-valid();}public function getTaskId(): string{return $this-taskId;}}class Scheduler{private SplQueue $tasks;public function __construct(){$this-tasks new SplQueue();}public function add(Task $task): void{$this-tasks-enqueue($task);}public function run(): void{while (!$this-tasks-isEmpty()) {$task $this-tasks-dequeue();$task-run();if (!$task-isFinished()) {$this-tasks-enqueue($task);}}}}// 模拟IO操作function ioOperation(string $name, int $ms): Generator{echo {$name}: 开始 ({$ms}ms)\n;yield; // 模拟异步等待echo {$name}: 完成\n;}$scheduler new Scheduler();$scheduler-add(new Task(A, ioOperation(请求API1, 2000)));$scheduler-add(new Task(B, ioOperation(请求API2, 1000)));$scheduler-add(new Task(C, ioOperation(请求API3, 1500)));$start microtime(true);$scheduler-run();echo 总耗时: . round((microtime(true) - $start) * 1000) . ms\n;?Swoole协程的使用方式php// Swoole协程use function Swoole\Coroutine\go;use function Swoole\Coroutine\run;function httpGet(string $url): string{$cli new Swoole\Coroutine\Http\Client(parse_url($url, PHP_URL_HOST), 80);$cli-get(parse_url($url, PHP_URL_PATH));return $cli-body;}function mysqlQuery(string $sql): array{$swoole_mysql new Swoole\Coroutine\MySQL();$swoole_mysql-connect([host 127.0.0.1,port 3306,user root,password ,database test,]);return $swoole_mysql-query($sql);}run(function () {// 并发执行多个HTTP请求$results [];go(function () use ($results) {$results[api1] httpGet(http://api.example.com/data1);});go(function () use ($results) {$results[api2] httpGet(http://api.example.com/data2);});go(function () use ($results) {$results[users] mysqlQuery(SELECT * FROM users LIMIT 10);});// 等待所有协程完成echo 所有请求完成\n;});?协程通道用于协程间通信phpuse Swoole\Coroutine\Channel;use function Swoole\Coroutine\go;use function Swoole\Coroutine\run;run(function () {$channel new Channel(10);// 生产者协程go(function () use ($channel) {for ($i 1; $i 10; $i) {$channel-push(数据{$i});echo 生产: 数据{$i}\n;}$channel-close();});// 消费者协程go(function () use ($channel) {while (true) {$data $channel-pop();if ($data false) break;echo 消费: {$data}\n;}});});?协程和普通函数的区别是协程可以暂停和恢复执行。在IO操作时协程自动让出CPU等IO完成后再恢复执行。这让单进程可以处理大量并发连接而不需要创建大量线程。理解协程的原理能更好地利用Swoole等高性能框架的能力。