本文目录导读:

我来详细介绍PHP中的集合(Collection) 和流式操作(Stream Operations)。
PHP集合操作
基础数组集合操作
<?php
// 基础集合数据
$users = [
['id' => 1, 'name' => 'Alice', 'age' => 25, 'city' => 'Beijing'],
['id' => 2, 'name' => 'Bob', 'age' => 30, 'city' => 'Shanghai'],
['id' => 3, 'name' => 'Charlie', 'age' => 22, 'city' => 'Beijing'],
['id' => 4, 'name' => 'David', 'age' => 35, 'city' => 'Guangzhou'],
];
// 过滤
$beijingUsers = array_filter($users, fn($user) => $user['city'] === 'Beijing');
// 映射
$names = array_map(fn($user) => $user['name'], $users);
// 排序
usort($users, fn($a, $b) => $a['age'] - $b['age']);
// 分组
$groupByCity = [];
foreach ($users as $user) {
$groupByCity[$user['city']][] = $user;
}
使用Laravel Collection
<?php
use Illuminate\Support\Collection;
$collection = collect([
['id' => 1, 'name' => 'Alice', 'age' => 25],
['id' => 2, 'name' => 'Bob', 'age' => 30],
['id' => 3, 'name' => 'Charlie', 'age' => 22],
]);
// 链式操作
$result = $collection
->where('age', '>', 23)
->sortBy('name')
->take(2)
->values()
->toArray();
// 高级操作
$averageAge = $collection->avg('age');
$maxAge = $collection->max('age');
$groupByName = $collection->groupBy(function($item) {
return strtoupper(substr($item['name'], 0, 1));
});
自定义Collection类
<?php
class SimpleCollection implements ArrayAccess, Countable, IteratorAggregate {
private array $items;
public function __construct(array $items = []) {
$this->items = $items;
}
// 过滤
public function filter(callable $callback): self {
return new self(array_filter($this->items, $callback));
}
// 映射
public function map(callable $callback): self {
return new self(array_map($callback, $this->items));
}
// 排序
public function sort(callable $callback): self {
$items = $this->items;
usort($items, $callback);
return new self($items);
}
// 获取最大值
public function max(?string $key = null): mixed {
if ($key === null) {
return max($this->items);
}
return max(array_column($this->items, $key));
}
// 链式操作示例
public function processChain(): self {
return $this
->filter(fn($item) => $item['active'] === true)
->sort(fn($a, $b) => $a['priority'] <=> $b['priority'])
->map(fn($item) => array_merge($item, ['processed' => true]));
}
public function getIterator(): ArrayIterator {
return new ArrayIterator($this->items);
}
public function count(): int {
return count($this->items);
}
public function offsetExists($offset): bool {
return isset($this->items[$offset]);
}
public function offsetGet($offset): mixed {
return $this->items[$offset] ?? null;
}
public function offsetSet($offset, $value): void {
if ($offset === null) {
$this->items[] = $value;
} else {
$this->items[$offset] = $value;
}
}
public function offsetUnset($offset): void {
unset($this->items[$offset]);
}
}
PHP流式操作
流式文件处理
<?php
// 读取大文件
function processLargeFile(string $filename, callable $handler): void {
$handle = fopen($filename, 'r');
if ($handle === false) {
throw new RuntimeException("Cannot open file: $filename");
}
while (($line = fgets($handle)) !== false) {
$handler(trim($line));
}
fclose($handle);
}
// 使用生成器实现流式处理
function readLines(string $filename): Generator {
$handle = fopen($filename, 'r');
if ($handle === false) {
throw new RuntimeException("Cannot open file: $filename");
}
while (($line = fgets($handle)) !== false) {
yield trim($line);
}
fclose($handle);
}
// 使用示例
$lines = readLines('large_file.txt');
foreach ($lines as $lineNumber => $line) {
echo "Line $lineNumber: $line\n";
}
流式数据转换管道
<?php
class StreamPipeline {
private array $operations = [];
private mixed $data;
public function __construct(mixed $data) {
$this->data = $data;
}
public function filter(callable $callback): self {
$this->operations[] = function($data) use ($callback) {
return array_filter($data, $callback);
};
return $this;
}
public function map(callable $callback): self {
$this->operations[] = function($data) use ($callback) {
return array_map($callback, $data);
};
return $this;
}
public function reduce(callable $callback, mixed $initial = null): self {
$this->operations[] = function($data) use ($callback, $initial) {
return array_reduce($data, $callback, $initial);
};
return $this;
}
public function execute(): mixed {
$result = $this->data;
foreach ($this->operations as $operation) {
$result = $operation($result);
}
return $result;
}
}
// 使用示例
$pipeline = new StreamPipeline([1, 2, 3, 4, 5, 6]);
$result = $pipeline
->filter(fn($n) => $n % 2 === 0) // 只保留偶数
->map(fn($n) => $n * 2) // 每个数乘以2
->reduce(fn($carry, $n) => $carry + $n, 0) // 求和
->execute();
echo $result; // 输出: 24
高级流式操作实现
<?php
class Stream {
private array $data;
private array $pipeline = [];
public function __construct(array $data) {
$this->data = $data;
}
public static function of(array $data): self {
return new self($data);
}
// 过滤操作
public function filter(callable $predicate): self {
$this->pipeline[] = function($data) use ($predicate) {
return array_values(array_filter($data, $predicate));
};
return $this;
}
// 映射操作
public function map(callable $mapper): self {
$this->pipeline[] = function($data) use ($mapper) {
return array_map($mapper, $data);
};
return $this;
}
// 扁平化映射
public function flatMap(callable $mapper): self {
$this->pipeline[] = function($data) use ($mapper) {
$result = [];
foreach ($data as $item) {
$result = array_merge($result, $mapper($item));
}
return $result;
};
return $this;
}
// 去重
public function distinct(): self {
$this->pipeline[] = function($data) {
return array_values(array_unique($data, SORT_REGULAR));
};
return $this;
}
// 排序
public function sorted(?callable $comparator = null): self {
$this->pipeline[] = function($data) use ($comparator) {
$sorted = $data;
if ($comparator) {
usort($sorted, $comparator);
} else {
sort($sorted);
}
return $sorted;
};
return $this;
}
// 限制数量
public function limit(int $limit): self {
$this->pipeline[] = function($data) use ($limit) {
return array_slice($data, 0, $limit);
};
return $this;
}
// 跳过
public function skip(int $count): self {
$this->pipeline[] = function($data) use ($count) {
return array_slice($data, $count);
};
return $this;
}
// 收集结果
public function collect(): array {
$result = $this->data;
foreach ($this->pipeline as $operation) {
$result = $operation($result);
}
return $result;
}
// 获取第一个元素
public function first(): mixed {
$result = $this->collect();
return !empty($result) ? $result[0] : null;
}
// 统计
public function count(): int {
return count($this->collect());
}
// 判断是否所有元素满足条件
public function allMatch(callable $predicate): bool {
foreach ($this->data as $item) {
if (!$predicate($item)) {
return false;
}
}
return true;
}
// 判断是否存在满足条件的元素
public function anyMatch(callable $predicate): bool {
foreach ($this->data as $item) {
if ($predicate($item)) {
return true;
}
}
return false;
}
}
// 使用示例
$people = [
['name' => 'Alice', 'age' => 25, 'department' => 'IT'],
['name' => 'Bob', 'age' => 30, 'department' => 'HR'],
['name' => 'Charlie', 'age' => 22, 'department' => 'IT'],
['name' => 'David', 'age' => 35, 'department' => 'Finance'],
];
$result = Stream::of($people)
->filter(fn($p) => $p['age'] > 23)
->map(fn($p) => [
'name' => $p['name'],
'age' => $p['age'],
'seniority' => $p['age'] > 30 ? 'Senior' : 'Junior'
])
->sorted(fn($a, $b) => $a['age'] <=> $b['age'])
->limit(3)
->collect();
print_r($result);
惰性求值实现
<?php
class LazyStream {
private Generator $generator;
private array $operations = [];
public function __construct(Generator $generator) {
$this->generator = $generator;
}
public function filter(callable $predicate): self {
$this->operations[] = function(Generator $gen) use ($predicate) {
foreach ($gen as $item) {
if ($predicate($item)) {
yield $item;
}
}
};
return $this;
}
public function map(callable $mapper): self {
$this->operations[] = function(Generator $gen) use ($mapper) {
foreach ($gen as $item) {
yield $mapper($item);
}
};
return $this;
}
// 惰性执行,只在需要时计算结果
public function execute(): Generator {
$currentGen = $this->generator;
foreach ($this->operations as $operation) {
$currentGen = $operation($currentGen);
}
return $currentGen;
}
}
// 使用示例 - 处理大量数据
function generateLargeDataset(int $count): Generator {
for ($i = 0; $i < $count; $i++) {
yield ['id' => $i, 'value' => rand(1, 1000)];
}
}
$stream = new LazyStream(generateLargeDataset(1000000));
$result = $stream
->filter(fn($item) => $item['value'] > 500)
->map(fn($item) => $item['id'] * 2)
->execute();
// 只在遍历时真正计算
foreach ($result as $value) {
echo $value . "\n";
}
实际应用场景
数据清洗管道
<?php
class DataCleaningPipeline {
public function process(array $data): array {
return Stream::of($data)
->filter(fn($item) => !empty($item['email'])) // 过滤空邮箱
->map(fn($item) => [
...$item,
'email' => strtolower(trim($item['email'])), // 清洗数据
'phone' => preg_replace('/[^0-9]/', '', $item['phone'] ?? '')
])
->distinct() // 去重
->sorted(fn($a, $b) => $a['created_at'] <=> $b['created_at']) // 按时间排序
->collect();
}
}
报表生成
<?php
class ReportGenerator {
public function generateSalesReport(array $transactions): array {
return Stream::of($transactions)
->filter(fn($t) => $t['status'] === 'completed')
->groupBy(fn($t) => $t['product_id'])
->map(function($group) {
return [
'product_id' => $group[0]['product_id'],
'total_sales' => array_sum(array_column($group, 'amount')),
'count' => count($group),
'average' => array_sum(array_column($group, 'amount')) / count($group)
];
})
->sorted(fn($a, $b) => $b['total_sales'] <=> $a['total_sales'])
->take(10)
->collect();
}
}
这些集合和流式操作模式可以大幅提高PHP代码的可读性和维护性,特别适合数据处理、批量操作和管道式转换等场景。
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播