PHP合并多维JSON数据:按市场及Over/Under格式重构
PHP 多维JSON数据按市场类型整合实现方案
需求说明
将按bookmakers(如draftkings、fanduel)分层的NBA赛事数据,转换为按market(如player_assists、player_points)+ 投注类型(Over/Under)分类的结构,每个条目聚合不同博彩商的price和point字段。
实现思路
- 将JSON字符串解析为PHP数组,方便遍历操作
- 用市场key + 投注类型name + 球员描述description作为唯一标识,确保每个聚合条目不重复
- 嵌套遍历
bookmakers→markets→outcomes,将每个博彩商的价格和点位数据映射到对应聚合条目 - 最后将处理后的数组转为JSON格式
完整代码实现
<?php // 原始JSON数据 $jsonData = '{ "id": "a57c57a5c1d6581cf5b9fff6737827ce", "sport_key": "basketball_nba", "sport_title": "NBA", "commence_time": "2023-05-20T00:30:00Z", "home_team": "Boston Celtics", "away_team": "Miami Heat", "bookmakers": [ { "key": "draftkings", "title": "DraftKings", "markets": [ { "key": "player_assists", "last_update": "2023-05-18T18:58:05Z", "outcomes": [ { "name": "Over", "description": "Al Horford", "price": -130, "point": 2.5 }, { "name": "Under", "description": "Al Horford", "price": 100, "point": 2.5 } ] }, { "key": "player_points", "last_update": "2023-05-18T18:58:05Z", "outcomes": [ { "name": "Over", "description": "Al Horford", "price": -115, "point": 7.5 }, { "name": "Under", "description": "Al Horford", "price": -115, "point": 7.5 } ] } ] }, { "key": "fanduel", "title": "FanDuel", "markets": [ { "key": "player_assists", "last_update": "2023-05-18T18:57:22Z", "outcomes": [ { "name": "Over", "description": "Al Horford", "price": -128, "point": 2.5 }, { "name": "Under", "description": "Al Horford", "price": 100, "point": 2.5 } ] }, { "key": "player_points", "last_update": "2023-05-18T18:57:22Z", "outcomes": [ { "name": "Over", "description": "Al Horford", "price": -111, "point": 7.5 }, { "name": "Under", "description": "Al Horford", "price": -115, "point": 7.5 } ] } ] } ]}'; // 解析JSON为关联数组 $data = json_decode($jsonData, true); // 初始化结果数组 $result = []; // 遍历每个博彩商 foreach ($data['bookmakers'] as $bookmaker) { $bookmakerKey = $bookmaker['key']; // 遍历博彩商下的每个市场 foreach ($bookmaker['markets'] as $market) { $marketKey = $market['key']; // 遍历市场下的每个投注结果 foreach ($market['outcomes'] as $outcome) { // 生成唯一标识,确保同一市场、同一投注类型、同一球员的条目唯一 $uniqueKey = $marketKey . '_' . $outcome['name'] . '_' . $outcome['description']; // 如果该条目不存在,先初始化基础字段 if (!isset($result[$uniqueKey])) { $result[$uniqueKey] = [ 'description' => $outcome['description'], 'key' => $marketKey, 'name' => $outcome['name'] ]; } // 添加当前博彩商的价格和点位字段 $result[$uniqueKey][$bookmakerKey . '_price'] = $outcome['price']; $result[$uniqueKey][$bookmakerKey . '_point'] = $outcome['point']; } } } // 将关联数组转为索引数组(符合目标格式要求) $result = array_values($result); // 输出格式化后的JSON echo json_encode($result, JSON_PRETTY_PRINT); ?>
输出结果
执行上述代码后,将得到与期望完全一致的JSON结构:
[ { "description": "Al Horford", "key": "player_assists", "name": "Over", "draftkings_price": -130, "draftkings_point": 2.5, "fanduel_price": -128, "fanduel_point": 2.5 }, { "description": "Al Horford", "key": "player_assists", "name": "Under", "draftkings_price": 100, "draftkings_point": 2.5, "fanduel_price": 100, "fanduel_point": 2.5 }, { "description": "Al Horford", "key": "player_points", "name": "Over", "draftkings_price": -115, "draftkings_point": 7.5, "fanduel_price": -111, "fanduel_point": 7.5 }, { "description": "Al Horford", "key": "player_points", "name": "Under", "draftkings_price": -115, "draftkings_point": 7.5, "fanduel_price": -115, "fanduel_point": 7.5 } ]
关键说明
- 使用
$marketKey . '_' . $outcome['name'] . '_' . $outcome['description']作为唯一键,避免重复创建条目 - 动态生成博彩商对应的字段名(如
draftkings_price),确保扩展性——即使新增其他博彩商,代码无需修改即可兼容 - 最后用
array_values()将关联数组转为索引数组,符合目标JSON的结构要求
内容的提问来源于stack exchange,提问作者AJK
相关产品推荐
相关产品推荐

