今天冉冉博客带来一篇实用技术教程,主题是深入理解 PHP 匹配表达式。这些技巧经过实际项目验证,直接可用。
一、PHP 8 属性注解实战
PHP 8 引入的 Attributes(属性注解)让元数据声明更加优雅。在冉冉博客的开发中,我们大量使用注解来简化代码。
1.1 基础语法与使用场景
属性注解可以附加到类、方法、属性、参数等,常用于路由定义、依赖注入、验证规则、ORM 映射等场景。
// 定义路由注解
#[Attribute(Attribute::TARGET_METHOD)]
class Route {
public function __construct(
public string $path,
public string $method = 'GET'
) {}
}
// 使用注解
class UserController {
#[Route('/users', 'GET')]
public function index() { /* ... */ }
#[Route('/users/{id}', 'GET')]
public function show(int $id) { /* ... */ }
#[Route('/users', 'POST')]
public function store(Request $request) { /* ... */ }
}
1.2 反射读取注解
$reflector = new ReflectionClass(UserController::class);
foreach ($reflector->getMethods() as $method) {
$attributes = $method->getAttributes(Route::class);
foreach ($attributes as $attribute) {
$route = $attribute->newInstance();
echo "Route: {$route->method} {$route->path}\n";
}
}
二、Fiber 协程异步编程
PHP 8.1 引入的 Fiber 让 PHP 也能实现协程,为异步编程打开了新的大门。虽然不如 Node.js 成熟,但在特定场景下非常有用。
2.1 Fiber 基础概念
Fiber 是一种可以暂停和恢复执行的轻量级线程。与生成器不同,Fiber 可以从任意深度调用栈中挂起。
// 创建 Fiber
$fiber = new Fiber(function () {
echo "Fiber started\n";
$value = Fiber::suspend('suspended');
echo "Fiber resumed with: $value\n";
return 'done';
});
// 启动 Fiber
$result = $fiber->start();
echo "Main got: $result\n";
// 恢复 Fiber
$fiber->resume('hello');
2.2 异步 HTTP 请求示例
class AsyncHttp {
private array $fibers = [];
public function request(string $url): Fiber {
$fiber = new Fiber(function () use ($url) {
// 模拟异步请求
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
curl_close($ch);
return $result;
});
$this->fibers[] = $fiber;
return $fiber;
}
public function run(): array {
$results = [];
foreach ($this->fibers as $fiber) {
$results[] = $fiber->start();
}
return $results;
}
}
三、枚举类型最佳实践
PHP 8.1 引入的 Enum 让代码更加类型安全,替代了传统的常量定义方式。冉冉博客在状态管理、权限控制等场景大量使用枚举。
3.1 基础枚举与 backed 枚举
// 纯枚举
enum Status {
case Pending;
case Approved;
case Rejected;
}
// Backed 枚举(带值)
enum OrderStatus: string {
case Pending = 'pending';
case Paid = 'paid';
case Shipped = 'shipped';
case Delivered = 'delivered';
case Cancelled = 'cancelled';
public function label(): string {
return match($this) {
self::Pending => '待付款',
self::Paid => '已付款',
self::Shipped => '已发货',
self::Delivered => '已送达',
self::Cancelled => '已取消',
};
}
public function color(): string {
return match($this) {
self::Pending => 'yellow',
self::Paid => 'blue',
self::Shipped => 'purple',
self::Delivered => 'green',
self::Cancelled => 'red',
};
}
}
3.2 枚举在数据库中的应用
class Order {
public function __construct(
public int $id,
public OrderStatus $status
) {}
public function canCancel(): bool {
return in_array($this->status, [
OrderStatus::Pending,
OrderStatus::Paid
]);
}
}
// 从数据库读取
$order = new Order(
id: 1,
status: OrderStatus::from($row['status'])
);
四、只读属性与不可变对象
PHP 8.1 引入的 readonly 属性让创建不可变对象变得简单。这在领域驱动设计、值对象等场景中非常有用。
4.1 只读属性基础
class User {
public function __construct(
public readonly int $id,
public readonly string $email,
public readonly DateTimeImmutable $createdAt
) {}
}
$user = new User(1, 'ranran@example.com', new DateTimeImmutable());
// 以下会报错
// $user->id = 2; // Error: Cannot modify readonly property
4.2 值对象模式
readonly class Money {
public function __construct(
public int $amount,
public string $currency
) {}
public function add(Money $other): Money {
if ($this->currency !== $other->currency) {
throw new InvalidArgumentException('Currency mismatch');
}
return new Money(
$this->amount + $other->amount,
$this->currency
);
}
}
$price = new Money(1000, 'CNY');
$shipping = new Money(100, 'CNY');
$total = $price->add($shipping); // 返回新的 Money 对象
五、生产环境部署与监控
代码写得再好,部署不当也会影响性能。分享冉冉博客的生产环境部署经验。
5.1 PHP-FPM 进程管理
; www.conf 配置
pm = dynamic ; 动态进程管理
pm.max_children = 50 ; 最大子进程数
pm.start_servers = 5 ; 启动时进程数
pm.min_spare_servers = 5 ; 最小空闲进程
pm.max_spare_servers = 35 ; 最大空闲进程
pm.max_requests = 500 ; 每个进程处理请求数后重启
; 内存计算
; 假设每个 PHP 进程占用 30MB
; 服务器内存 2GB,留给 PHP 1GB
; max_children = 1024MB / 30MB ≈ 34
5.2 日志与监控
// 结构化日志
$logger->info('Order created', [
'order_id' => $order->id,
'user_id' => $order->userId,
'amount' => $order->amount,
'timestamp' => date('c')
]);
// 性能监控
$start = microtime(true);
$result = heavyOperation();
$duration = (microtime(true) - $start) * 1000;
if ($duration > 1000) {
$logger->warning('Slow query detected', [
'duration_ms' => $duration,
'operation' => 'heavyOperation'
]);
}
深入理解 PHP 匹配表达式就分享到这里。如果你觉得有用,欢迎收藏冉冉博客,获取更多网站编程和实用工具相关的技术文章。
© 版权声明
文章版权归作者所有,未经允许请勿转载。
THE END
















暂无评论内容