PHP并发处理的三种高效解决方案
PHP 并发处理的三种常见且高效的并发处理手段:多进程(PCNTL)、多线程/多任务(Parallel 扩展)、协程/异步(Swoole)。每一部分都有完整的代码示例、ASCII 流程图和深入的原理说明,帮助你快速掌握 PHP 在不同场景下的并发实现方法。
一、并发处理的必要性与常见场景
在 Web 应用或脚本中,我们常会遇到如下需要并发处理的场景:
- 并行发起多个网络请求(如抓取多个第三方接口数据,批量爬虫)
- 执行大量 I/O 密集型任务(如大批量文件读写、图像处理、数据库导入导出)
- 后台任务队列消费(如将若干任务交给多进程或多线程并行处理,提高吞吐)
- 长连接或异步任务(如 WebSocket、消息订阅、实时推送)
如果依赖传统的“串行”方式,一个一个地依次执行,就会导致等待时间累加、响应速度下降、CPU/IO 资源无法充分利用。通过并发(并行或异步)处理,可以显著提升脚本整体吞吐,并降低单次操作的总耗时。
在 PHP 领域,常见的三种并发思路是:
- 多进程(Process):通过
pcntl_fork()
创建子进程,各自独立执行任务,适合计算与 I/O 混合型场景。 - 多线程/多任务(Thread/Task):使用
parallel
或pthreads
扩展,在同一进程内启动多个执行环境,适合轻量计算与共享内存场景。 - 协程/异步(Coroutine/Async):以 Swoole 为代表,通过协程或事件循环驱动单进程并发,极大降低上下文切换开销,适合大并发 I/O 场景。
下面我们依次详细介绍这三种并发手段,给出代码示例、ASCII 图解与性能要点。
二、方案一:多进程 —— 使用 PCNTL 扩展
2.1 基本原理
- 概念:在 Unix-like 系统(Linux、macOS)中,进程(Process)是操作系统分配资源的基本单位。通过调用
pcntl_fork()
,父进程会复制出一个子进程,两者从 fork 点开始各自独立运行。 优势:
- 资源隔离:父子进程各自拥有独立的内存空间,互不干扰,适合运行耗时耗内存的任务。
- 稳定可靠:某个子进程 crash 不会直接影响父进程或其他子进程。
- 利用多核:在多核 CPU 上,多个进程可并行调度,提高计算与 I/O 并行度。
劣势:
- 内存开销大:每个子进程都会复制父进程的内存页,fork 时会产生写时复制(Copy-on-Write)。
- 上下文切换成本:系统调度多进程会带来一定开销,频繁 fork/exit 会影响效率。
- 开发复杂度高:需要手动回收子进程、避免僵尸进程,并处理进程间通信(若有需求)。
2.2 环境准备
- 确保 PHP 编译时开启了
--enable-pcntl
(多数 Linux 包管理器自带支持)。 - CLI 模式下运行。Web 环境(Apache/Nginx+PHP-FPM)通常不允许
pcntl_fork()
,需要从命令行执行脚本。 - PHP 7+ 建议版本,语法与功能更完善。
2.3 简单示例:并行执行多个任务
下面示例演示如何利用 pcntl_fork()
启动多个子进程并行执行任务(如访问 URL、处理数据),并在父进程中等待所有子进程结束。
<?php
// 文件:multi_process.php
// 要并行执行的“任务”:简单模拟网络请求或耗时计算
function doTask(int $taskId) {
echo "[子进程 {$taskId}] 开始任务,PID=" . getmypid() . "\n";
// 模拟耗时:随机 sleep 1~3 秒
$sleep = rand(1, 3);
sleep($sleep);
echo "[子进程 {$taskId}] 任务完成,用时 {$sleep} 秒\n";
}
// 任务数量(子进程数)
// 建议不要超过 CPU 核心数的 2 倍,否则上下文切换开销可能增大
$taskCount = 5;
$childPids = [];
// 父进程循环 fork
for ($i = 1; $i <= $taskCount; $i++) {
$pid = pcntl_fork();
if ($pid === -1) {
// fork 失败
die("无法 fork 子进程 #{$i}\n");
} elseif ($pid === 0) {
// 子进程分支
doTask($i);
// 子进程必须 exit,否则会继续执行父进程后续代码
exit(0);
} else {
// 父进程分支:记录子进程 PID,继续循环创建下一子进程
$childPids[] = $pid;
}
}
// 父进程:等待所有子进程完成
echo "[父进程] 等待子进程完成...\n";
foreach ($childPids as $pid) {
// pcntl_waitpid() 阻塞等待指定子进程结束
pcntl_waitpid($pid, $status);
echo "[父进程] 子进程 PID={$pid} 已结束,状态={$status}\n";
}
echo "[父进程] 所有子进程已完成,退出。\n";
运行方式
php multi_process.php
ASCII 流程图
┌─────────────────────────────────────────────────────────┐
│ 父进程 (PID = 1000) │
└─────────────────────────────────────────────────────────┘
│
│ pcntl_fork() 创建子进程 1 (PID=1001)
↓
┌─────────────────┐ ┌─────────────────┐
│ 父进程 继续循环 │ │ 子进程 1 执行 doTask(1) │
│ (记录 PID=1001) │ │ │
└─────────────────┘ └─────────────────┘
│ │
│ pcntl_fork() 创建子进程 2 │
↓ ↓
┌─────────────────┐ ┌────────────────────┐
│ 父进程 继续循环 │ │ 子进程 2 执行 doTask(2) │
│ (记录 PID=1002) │ │ │
└─────────────────┘ └────────────────────┘
│ │
⋮ ⋮
│ │
│ pcntl_fork() 创建子进程 5 │
↓ ↓
┌─────────────────┐ ┌────────────────────┐
│ 父进程 循环结束 │ │ 子进程 5 执行 doTask(5) │
│ (记录 PID=1005) │ │ │
└─────────────────┘ └────────────────────┘
│ │
│ 父进程调用 pcntl_waitpid() 等待各子进程结束
└─────────────────────────────────────────────────>
│
┌───────────────────────────────────────┐
│ 子进程各自执行完 doTask() 后 exit(0) │
└───────────────────────────────────────┘
↓
父进程输出“子进程 PID 已结束”消息
↓
父进程等待完毕后退出脚本
解析与要点
pcntl_fork()
:返回值- 在父进程中,返回子进程的 PID(>0)
- 在子进程中,返回 0
- 失败时,返回 -1
- 子进程执行完毕后必须
exit(0)
,否则子进程会继续执行父进程后续代码,导致进程混淆。 - 父进程通过
pcntl_waitpid($pid, $status)
阻塞等待指定子进程结束,并获取退出状态。 - 最好将任务量与 CPU 核心数做简要衡量,避免创建过多子进程带来过大上下文切换成本。
三、方案二:多线程/多任务 —— 使用 Parallel 扩展
注意:PHP 官方不再维护pthreads
扩展,且仅支持 CLI ZTS(线程安全)版。更推荐使用 PHP 7.4+ 的 Parallel 扩展,能在 CLI 下创建“并行运行环境(Runtime)”,每个Runtime
都是独立的线程环境,可以运行\parallel\Future
任务。
3.1 基本原理
- Parallel 扩展:为 PHP 提供了一套纯 PHP 层的并行处理 API,通过
parallel\Runtime
在后台启动一个线程环境,每个环境会有自己独立的上下文,可以运行指定的函数或脚本。 优势:
- 内存隔离:与 pcntl 类似,
Runtime
内的代码有自己独立内存,不会与主线程直接共享变量,避免竞争。 - API 友好:更类似“线程池+任务队列”模型,提交任务后可异步获取结果。
- 无需 ZTS:Parallel 扩展无需编译成 ZTS 版本的 PHP,即可使用。
- 内存隔离:与 pcntl 类似,
劣势:
- 环境要求:仅支持 PHP 7.2+,且需先通过
pecl install parallel
安装扩展。 - 内存开销:每个
Runtime
会在后台生成一个线程及其上下文,资源消耗不可忽视。 - 不支持 Web 环境:仅能在 CLI 下运行。
- 环境要求:仅支持 PHP 7.2+,且需先通过
3.2 安装与检查
# 安装 Parallel 扩展
pecl install parallel
# 确保 php.ini 中已加载 parallel.so
echo "extension=parallel.so" >> /etc/php/7.4/cli/php.ini
# 验证
php -m | grep parallel
# 如果输出 parallel 则说明安装成功
3.3 简单示例:并行执行多个函数
以下示例演示如何使用 parallel\Runtime
和 Future
并行执行多个耗时函数,并在主线程中等待所有结果。
<?php
// 文件:parallel_example.php
use parallel\Runtime;
use parallel\Future;
// 自动加载如果使用 Composer,可根据实际情况调整
// require 'vendor/autoload.php';
// 模拟耗时函数:睡眠 1~3 秒
function taskFunction(int $taskId): string {
echo "[Thread {$taskId}] 开始任务,TID=" . getmypid() . "\n";
$sleep = rand(1, 3);
sleep($sleep);
return "[Thread {$taskId}] 完成任务,用时 {$sleep} 秒";
}
$taskCount = 5;
$runtimes = [];
$futures = [];
// 1. 创建多个 Runtime(相当于线程环境)
for ($i = 1; $i <= $taskCount; $i++) {
$runtimes[$i] = new Runtime(); // 新建线程环境
}
// 2. 向各 Runtime 提交任务
for ($i = 1; $i <= $taskCount; $i++) {
// run() 返回 Future 对象,可通过 Future->value() 获取执行结果(阻塞)
$futures[$i] = $runtimes[$i]->run(function(int $tid) {
return taskFunction($tid);
}, [$i]);
}
// 3. 主线程等待并获取所有结果
foreach ($futures as $i => $future) {
$result = $future->value(); // 阻塞到对应任务完成
echo $result . "\n";
}
// 4. 关闭线程环境(可选,PHP 会在脚本结束时自动回收)
foreach ($runtimes as $rt) {
$rt->close();
}
echo "[主线程] 所有并行任务已完成,退出。\n";
运行方式
php parallel_example.php
ASCII 流程图
┌──────────────────────────────────────────────────────┐
│ 主线程 (PID=2000) │
└──────────────────────────────────────────────────────┘
│ │ │ │ │
│ │ │ │ │
▼ ▼ ▼ ▼ ▼
┌────────┐ ┌────────┐ ┌────────┐ ┌────────┐ ┌────────┐
│Runtime1│ │Runtime2│ │Runtime3│ │Runtime4│ │Runtime5│ <- 每个都是一个独立线程环境
│ (TID) │ │ (TID) │ │ (TID) │ │ (TID) │ │ (TID) │
└───┬────┘ └───┬────┘ └───┬────┘ └───┬────┘ └───┬────┘
│ │ │ │ │
│ 提交任务 │ 提交任务 │ 提交任务 │ 提交任务 │ 提交任务
▼ ▼ ▼ ▼ ▼
[Thread1] [Thread2] [Thread3] [Thread4] [Thread5]
doTask(1) doTask(2) doTask(3) doTask(4) doTask(5)
│ │ │ │ │
└─────┬───────┴──┬─────────┴──┬───────────┴───┬──────┘
▼ ▼ ▼ ▼
主线程等待 future->value() ... Collect Results
解析与要点
new Runtime()
:为每个并行任务创建一个新的“线程环境”,内部会复制(序列化再反序列化)全局依赖。- 闭包函数传参:
run(function, [args])
中,闭包与传入参数会被序列化并发送到对应 Runtime 环境。 Future->value()
:阻塞等待目标线程返回执行结果。若当前 Future 已完成则立即返回。- 资源隔离:在闭包内部定义的函数
taskFunction
是通过序列化传给线程,并在新环境内执行,主线程无法直接访问线程内部变量。 - 关闭线程:可通过
$runtime->close()
将线程环境释放,但脚本结束时会自动回收,无需手动关闭也可。
四、方案三:协程/异步 —— 使用 Swoole 扩展
4.1 基本原理
- Swoole:一个为 PHP 提供高性能网络通信、异步 I/O、协程等功能的扩展。通过协程(Coroutine)机制,让 PHP 在单进程内实现类似“多线程”的并发效果。
- 协程:相比传统“线程”更轻量,切换时无需系统调度,几乎没有上下文切换成本。
优势:
- 高并发 I/O 性能:适合高并发网络请求、长连接、WebSocket 等场景。
- 简单语法:使用
go(function() { … })
即可创建协程,在协程内部可以像写同步代码一样写异步逻辑。 - 丰富生态:Swoole 内置 HTTP Server、WebSocket Server、定时器、Channel 等并发构建块。
劣势:
- 需要安装扩展:需先
pecl install swoole
或自行编译安装。 - 不适合全栈同步框架:若项目大量依赖同步阻塞式代码,需要做协程安全改造。
- 需使用 CLI 方式运行:不能像普通 PHP-FPM 一样被 Nginx 调用。
- 需要安装扩展:需先
4.2 安装与检查
# 安装 Swoole 最新稳定版本
pecl install swoole
# 确保 php.ini 中已加载 swoole.so
echo "extension=swoole.so" >> /etc/php/7.4/cli/php.ini
# 验证
php --ri swoole
# 会显示 Swoole 版本与配置信息
4.3 示例一:协程并行发起多 HTTP 请求
下面示例展示如何通过 Swoole 协程并发地发起多个 HTTP GET 请求,并在所有请求完成后收集响应。
<?php
// 文件:swoole_coro_http.php
use Swoole\Coroutine\Http\Client;
use Swoole\Coroutine;
// 要并行请求的 URL 列表
$urls = [
'http://httpbin.org/delay/2', // 延迟 2 秒返回
'http://httpbin.org/delay/1',
'http://httpbin.org/status/200',
'http://httpbin.org/uuid',
'http://httpbin.org/get'
];
// 协程入口
Co\run(function() use ($urls) {
$responses = [];
$wg = new Swoole\Coroutine\WaitGroup();
foreach ($urls as $index => $url) {
$wg->add(); // 增加等待组计数
go(function() use ($index, $url, &$responses, $wg) {
$parsed = parse_url($url);
$host = $parsed['host'];
$port = ($parsed['scheme'] === 'https') ? 443 : 80;
$path = $parsed['path'] . (isset($parsed['query']) ? "?{$parsed['query']}" : '');
$cli = new Client($host, $port, $parsed['scheme'] === 'https');
$cli->set(['timeout' => 5]);
$cli->get($path);
$body = $cli->body;
$status = $cli->statusCode;
$cli->close();
$responses[$index] = [
'url' => $url,
'status' => $status,
'body' => substr($body, 0, 100) . '…' // 为示例只截取前100字符
];
echo "[协程 {$index}] 请求 {$url} 完成,状态码={$status}\n";
$wg->done(); // 通知 WaitGroup 当前协程已完成
});
}
// 等待所有协程执行完毕
$wg->wait();
echo "[主协程] 所有请求已完成,共 " . count($responses) . " 条响应。\n";
print_r($responses);
});
运行方式
php swoole_coro_http.php
ASCII 流程图
┌───────────────────────────────────────────────────────────────────┐
│ 主协程 (Main Coroutine) │
└───────────────────────────────────────────────────────────────────┘
│ │ │ │ │
go()【】 go()【】 go()【】 go()【】 go()【】
│ │ │ │ │
▼ ▼ ▼ ▼ ▼
[协程 0] [协程 1] [协程 2] [协程 3] [协程 4]
send GET send GET send GET send GET send GET
await I/O await I/O await I/O await I/O await I/O
↑ ↑ ↑ ↑ ↑
I/O 完成 I/O 完成 I/O 完成 I/O 完成 I/O 完成
│ │ │ │ │
异步返回 异步返回 异步返回 异步返回 异步返回
│ │ │ │ │
协程 0 … 协程 4
写入 $responses … 写入 $responses
$wg->done() … $wg->done()
│ │ │ │ │
┌───────────────────────────────────────────────────────────────────┐
│ 主协程调用 $wg->wait() 阻塞,直到所有 $wg->done() 都执行完成 │
└───────────────────────────────────────────────────────────────────┘
↓
┌───────────────────────────────────────────────────────────────────┐
│ 打印所有并行请求结果并退出脚本 │
└───────────────────────────────────────────────────────────────────┘
解析与要点
\Swoole\Coroutine\run()
:启动一个全新的协程容器环境,主协程会在回调内部启动。go(function() { … })
:创建并切换到一个新协程执行闭包函数。Swoole\Coroutine\Http\Client
:已被协程化的 HTTP 客户端,可在协程中非阻塞地进行网络请求。WaitGroup
:相当于 Go 语言的 WaitGroup,用于等待多个协程都调用$wg->done()
,再从$wg->wait()
的阻塞中继续执行。- 单进程多协程:所有协程都跑在同一个系统进程中,不会像多进程/多线程那样切换内核调度,协程的上下文切换几乎没有开销。
4.4 示例二:使用 Swoole Process 实现多进程任务处理
如果项目无法全部迁移到协程模式,也可以使用 Swoole 提供的 Process 类来创建多进程,并结合管道/消息队列等在进程间通信。
以下示例演示如何用 Swoole Process 创建 3 个子进程并行执行任务,并在父进程中通过管道收集结果。
<?php
// 文件:swoole_process.php
use Swoole\Process;
// 要并行执行的耗时函数
function doJob(int $jobId) {
echo "[子进程 {$jobId}] (PID=" . getmypid() . ") 开始任务\n";
$sleep = rand(1, 3);
sleep($sleep);
$result = "[子进程 {$jobId}] 任务完成,用时 {$sleep} 秒";
return $result;
}
$processCount = 3;
$childProcesses = [];
// 父进程创建多个 Swoole\Process
for ($i = 1; $i <= $processCount; $i++) {
// 1. 定义子进程回调,使用匿名函数捕获 $i 作为任务编号
$process = new Process(function(Process $worker) use ($i) {
// 子进程内部执行
$result = doJob($i);
// 将结果写入管道,父进程可读取
$worker->write($result);
// 退出子进程
$worker->exit(0);
}, true, SOCK_DGRAM); // 启用管道
$pid = $process->start();
$childProcesses[$i] = ['pid' => $pid, 'pipe' => $process];
}
// 父进程:等待并读取子进程通过管道写入的数据
foreach ($childProcesses as $i => $info) {
$pipe = $info['pipe'];
// 阻塞读取子进程写入管道的数据
$data = $pipe->read();
echo "[父进程] 收到子进程 {$i} 结果:{$data}\n";
// 等待子进程退出,避免僵尸进程
Process::wait(true);
}
echo "[父进程] 所有子进程处理完成,退出。\n";
运行方式
php swoole_process.php
ASCII 流程图
┌──────────────────────────────────────────────────────────┐
│ 父进程 (PID=3000) │
└──────────────────────────────────────────────────────────┘
│ │ │
│ │ │
▼ ▼ ▼
┌────────┐ ┌────────┐ ┌────────┐
│Proc #1 │ │Proc #2 │ │Proc #3 │
│(PID) │ │(PID) │ │(PID) │
└───┬────┘ └───┬────┘ └───┬────┘
│ │ │
│ doJob(1) │ doJob(2) │ doJob(3)
│ │ │
│ write “结果” │ write “结果” │ write “结果”
▼ ▼ ▼
父进程从管道中 父进程从管道中 父进程从管道中
读到结果 1 读到结果 2 读到结果 3
│ │ │
└─────────────┴─────────────┘
│
父进程调用 Process::wait() 回收子进程
↓
父进程输出“所有子进程完成”后退出
解析与要点
new Process(callable, true, SOCK_DGRAM)
:第二个参数true
表示启用管道通信;第三个参数指定管道类型(SOCK_DGRAM
或SOCK_STREAM
)。- 子进程写入管道:调用
$worker->write($data)
,父进程通过$process->read()
获取数据。 - 父进程回收子进程:使用
Process::wait()
(或Process::wait(true)
)等待任意子进程退出,并避免产生僵尸进程。 - Swoole Process 与 PCNTL 的区别:前者封装更完善,有更方便的进程管理 API,但本质依然是多进程模型。
五、三种方案对比与选型建议
特性 / 方案 | 多进程(PCNTL) | 多线程/多任务(Parallel) | 协程/异步(Swoole) |
---|---|---|---|
并发模型 | 操作系统原生进程 | PHP 用户态线程环境 | 协程(用户态调度,单进程) |
安装与启用 | PHP CLI + pcntl 扩展 | PHP 7.2+ + parallel 扩展 | PHP 7.x + swoole 扩展 |
内存开销 | 每个子进程复制父进程内存(COW) | 每个 Runtime 启动独立线程,需复制上下文 | 单进程内协程切换,无额外线程上下文 |
上下文切换开销 | 较高(内核调度) | 较高(线程调度) | 非常低(协程切换由 Swoole 管理) |
平台兼容性 | 仅 CLI(Unix-like) | 仅 CLI(PHP 7.2+) | 仅 CLI(Unix-like/Windows,都支持) |
编程复杂度 | 中等(手动 fork/wait、IPC) | 低(类似线程池、Future 模式) | 低(异步写法接近同步,可用 channel、WaitGroup) |
适用场景 | 计算密集型、多核利用;进程隔离 | 中小规模并行计算;任务隔离 | 高并发 I/O;网络爬虫;实时通信 |
数据共享 | 进程间需通过管道/消息队列等 IPC | 线程间需序列化数据到 Runtime | 协程可共享全局变量(需注意同步) |
稳定性 | 高:一个子进程崩溃不影响父进程 | 较高:线程隔离度不如进程,但 Runtime 崩溃会影响父 | 高:协程内抛异常可捕获,单进程风险较低 |
5.1 选型建议
纯 CPU 密集型任务(如数据批量计算、图像处理):
- 建议使用 多进程(PCNTL),能够充分利用多核 CPU,且进程间隔离性好。
分布式任务调度、轻量并行计算(如同时处理多个独立小任务):
- 可以考虑 Parallel 扩展,API 更简单,适合 PHP 内部任务并行。
大量并发网络请求、I/O 密集型场景(如批量爬虫、聊天室、长连接服务):
- 强烈推荐 Swoole 协程,其异步 I/O 性能远超多进程/多线程,并发量可达数万级别。
小型脚本并发需求(如定时脚本并行处理少量任务,不想引入复杂扩展):
- 使用 PCNTL 即可,开发成本低,无需额外安装第三方扩展。
六、常见问题与注意事项
PCNTL 进程数过多导致内存耗尽
- 在多进程模式下,若一次性 fork 过多子进程(如上百个),会瞬间占用大量内存,可能触发 OOM。
- 建议按 CPU 核心数设定进程数,或按业务量使用固定大小的进程池,并用队列控制任务分发。
Parallel 运行时环境上下文传递限制
- Parallel 会序列化全局变量与闭包,若闭包中捕获了不可序列化资源(如数据库连接、Socket),会导致失败。
- 最好将要执行的代码与其依赖的类、函数文件放在同一脚本中,或先在 Runtime 内重新加载依赖。
Swoole 协程中不可使用阻塞 I/O
- 在协程中必须使用 Swoole 提供的协程化 I/O(如
Co\MySQL\
、Co\Http\Client
)或 PHP 原生的非阻塞流程(如file_get_contents
会阻塞整个进程)。 - 若使用阻塞 I/O,整个进程会被挂起,丧失协程并发优势。
- 在协程中必须使用 Swoole 提供的协程化 I/O(如
进程/协程内错误处理
- 子进程/子协程内发生致命错误不会直接中断父进程,但需要在父进程中捕获(如 PCNTL 的
pcntl_signal(SIGCHLD, ...)
或 Swoole 协程模式下的 try/catch)。 - 建议在子进程或协程内部加上异常捕获,并在写入管道或 Future 返回错误信息,以便父进程统一处理。
- 子进程/子协程内发生致命错误不会直接中断父进程,但需要在父进程中捕获(如 PCNTL 的
跨平台兼容性
- PCNTL 仅在 Linux/macOS 环境可用,Windows 不支持。
- Parallel 在 Windows、Linux 都可用,但需要 PECL 安装。
- Swoole 支持多平台,Windows 下也可正常编译与运行,但需使用对应的 DLL 文件。
七、总结
本文系统地介绍了 PHP 并发处理的三种高效解决方案:
多进程(PCNTL)
- 通过
pcntl_fork()
启动子进程并行运行任务,适合计算密集型或需要进程隔离的场景。 - 示例中演示了如何 fork 五个子进程并 parallel 执行固定任务,并通过
pcntl_waitpid()
等待子进程结束。
- 通过
多线程/多任务(Parallel 扩展)
- 利用
parallel\Runtime
创建线程环境并提交闭包任务,以Future->value()
等待结果,适合中小规模并行任务。 - 相比 PCNTL 更易管理,API 友好,但仍需在 CLI 环境下运行,且需先安装
parallel
扩展。
- 利用
协程/异步(Swoole 扩展)
- 以协程为基础,在单进程内实现高并发 I/O 操作。示例演示了协程并行发起多 HTTP 请求,使用
WaitGroup
整合结果,适合高并发网络场景。 - Swoole 还提供
Process
类,可用于多进程管理。
- 以协程为基础,在单进程内实现高并发 I/O 操作。示例演示了协程并行发起多 HTTP 请求,使用
最后,结合不同场景与业务需求,进行合理选型:
- CPU 密集型:优先 PCNTL 多进程。
- 轻量并行:优先 Parallel 多任务。
- 高并发 I/O:优先 Swoole 协程异步。
评论已关闭