php项目统计SofaScore综合评分?

wen PHP项目 2

本文目录导读:

php项目统计SofaScore综合评分?

  1. 获取SofaScore API数据
  2. 综合评分统计模型
  3. 数据存储模块
  4. 使用示例
  5. 数据库表结构
  6. 注意事项

在PHP项目中统计SofaScore综合评分,通常需要从SofaScore API获取球员或球队的评分数据,以下是完整的实现方案:

获取SofaScore API数据

API认证和请求配置

<?php
class SofaScoreAPI {
    private $apiKey;
    private $baseUrl = 'https://api.sofascore.com/api/v1';
    private $headers;
    public function __construct($apiKey) {
        $this->apiKey = $apiKey;
        $this->headers = [
            'Authorization: Bearer ' . $apiKey,
            'Accept: application/json',
            'User-Agent: MyFootballApp/1.0'
        ];
    }
    /**
     * 获取球员评分数据
     * @param int $playerId 球员ID
     * @return array 球员评分数据
     */
    public function getPlayerRatings($playerId) {
        $url = $this->baseUrl . "/player/{$playerId}/ratings";
        return $this->makeRequest($url);
    }
    /**
     * 获取球队球员评分列表
     * @param int $teamId 球队ID
     * @param int $seasonId 赛季ID
     * @return array 球员评分列表
     */
    public function getTeamPlayerRatings($teamId, $seasonId) {
        $url = $this->baseUrl . "/team/{$teamId}/players/{$seasonId}";
        return $this->makeRequest($url);
    }
    /**
     * 获取比赛评分
     * @param int $eventId 比赛事件ID
     * @return array 比赛评分数据
     */
    public function getEventRatings($eventId) {
        $url = $this->baseUrl . "/event/{$eventId}/ratings";
        return $this->makeRequest($url);
    }
    private function makeRequest($url) {
        $ch = curl_init($url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
        curl_setopt($ch, CURLOPT_HTTPHEADER, $this->headers);
        curl_setopt($ch, CURLOPT_TIMEOUT, 30);
        $response = curl_exec($ch);
        $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
        curl_close($ch);
        if ($httpCode !== 200) {
            throw new Exception("API请求失败: HTTP {$httpCode}");
        }
        return json_decode($response, true);
    }
}

综合评分统计模型

<?php
class SofaScoreRatingAggregator {
    // 评分权重配置
    private $weights = [
        'matches' => 0.4,        // 出场次数权重
        'avg_rating' => 0.3,     // 平均评分权重
        'consistency' => 0.2,    // 稳定性权重
        'trend' => 0.1           // 近期趋势权重
    ];
    /**
     * 计算球员综合评分
     * @param array $playerRatings 球员评分数据
     * @return array 综合评分结果
     */
    public function calculateCompositeRating($playerRatings) {
        if (empty($playerRatings) || empty($playerRatings['data'])) {
            return null;
        }
        $data = $playerRatings['data'];
        // 基础统计
        $matches = count($data);
        $sum = 0;
        $ratings = [];
        foreach ($data as $match) {
            if (isset($match['rating']) && $match['rating'] > 0) {
                $sum += $match['rating'];
                $ratings[] = $match['rating'];
            }
        }
        $avgRating = $matches > 0 ? round($sum / $matches, 2) : 0;
        // 稳定性(标准差计算)
        $consistency = $this->calculateConsistency($ratings, $avgRating);
        // 近期趋势(最近5场比赛)
        $trend = $this->calculateTrend($ratings);
        // 综合评分计算
        $compositeScore = (
            $matches * $this->weights['matches'] +
            $avgRating * $this->weights['avg_rating'] +
            $consistency * $this->weights['consistency'] +
            $trend * $this->weights['trend']
        );
        // 规范化为1-10分制
        $compositeScore = min(10, max(1, $compositeScore));
        return [
            'composite_score' => round($compositeScore, 2),
            'matches_played' => $matches,
            'avg_rating' => $avgRating,
            'consistency_score' => round($consistency, 2),
            'trend_score' => round($trend, 2),
            'max_rating' => max($ratings),
            'min_rating' => min($ratings),
            'last_matches' => array_slice($ratings, -5)
        ];
    }
    /**
     * 计算稳定性分数
     * @param array $ratings 评分数组
     * @param float $avg 平均评分
     * @return float 稳定性得分
     */
    private function calculateConsistency($ratings, $avg) {
        if (count($ratings) < 1) {
            return 0;
        }
        $variance = 0;
        $n = count($ratings);
        foreach ($ratings as $rating) {
            $variance += pow($rating - $avg, 2);
        }
        $stdDev = sqrt($variance / $n);
        // 标准差越小稳定性越高,转换为10分制
        $consistencyScore = 10 - ($stdDev * 5);
        return max(1, min(10, $consistencyScore));
    }
    /**
     * 计算近期趋势
     * @param array $ratings 评分数组
     * @return float 趋势得分
     */
    private function calculateTrend($ratings) {
        if (count($ratings) < 3) {
            return 5; // 数据不足时返回中等分数
        }
        // 取最近5场(或所有)比赛
        $recentMatches = array_slice($ratings, -5);
        $n = count($recentMatches);
        if ($n < 2) {
            return 5;
        }
        // 简单线性回归计算趋势
        $x = range(1, $n);
        $xAvg = array_sum($x) / $n;
        $yAvg = array_sum($recentMatches) / $n;
        $numerator = 0;
        $denominator = 0;
        for ($i = 0; $i < $n; $i++) {
            $numerator += ($x[$i] - $xAvg) * ($recentMatches[$i] - $yAvg);
            $denominator += pow($x[$i] - $xAvg, 2);
        }
        if ($denominator == 0) {
            return 5;
        }
        $slope = $numerator / $denominator;
        // 将斜率转换为趋势分数 (0-10)
        $trendScore = 5 + ($slope * 2);
        return max(1, min(10, $trendScore));
    }
}

数据存储模块

<?php
class RatingRepository {
    private $db;
    public function __construct($dbConnection) {
        $this->db = $dbConnection;
    }
    /**
     * 保存球员评分数据
     */
    public function savePlayerRating($playerId, $teamId, $eventId, $rating, $matchDate) {
        $sql = "INSERT INTO player_ratings 
                (player_id, team_id, event_id, rating, match_date) 
                VALUES (?, ?, ?, ?, ?)
                ON DUPLICATE KEY UPDATE rating = VALUES(rating)";
        $stmt = $this->db->prepare($sql);
        return $stmt->execute([$playerId, $teamId, $eventId, $rating, $matchDate]);
    }
    /**
     * 获取球员历史评分
     */
    public function getPlayerRatings($playerId, $limit = 30) {
        $sql = "SELECT rating, match_date 
                FROM player_ratings 
                WHERE player_id = ? 
                ORDER BY match_date DESC 
                LIMIT ?";
        $stmt = $this->db->prepare($sql);
        $stmt->execute([$playerId, $limit]);
        return $stmt->fetchAll(PDO::FETCH_ASSOC);
    }
    /**
     * 获取球员综合评分缓存
     */
    public function getCachedCompositeRating($playerId) {
        $sql = "SELECT composite_score FROM player_composite_ratings 
                WHERE player_id = ? 
                AND updated_at > DATE_SUB(NOW(), INTERVAL 24 HOUR)";
        $stmt = $this->db->prepare($sql);
        $stmt->execute([$playerId]);
        $result = $stmt->fetch(PDO::FETCH_ASSOC);
        return $result ? $result['composite_score'] : null;
    }
    /**
     * 缓存综合评分
     */
    public function cacheCompositeRating($playerId, $compositeScore) {
        $sql = "INSERT INTO player_composite_ratings (player_id, composite_score, updated_at) 
                VALUES (?, ?, NOW())
                ON DUPLICATE KEY UPDATE composite_score = VALUES(composite_score), updated_at = NOW()";
        $stmt = $this->db->prepare($sql);
        return $stmt->execute([$playerId, $compositeScore]);
    }
}

使用示例

<?php
// 配置文件
$config = [
    'api_key' => 'your_sofascore_api_key',
    'db_host' => 'localhost',
    'db_name' => 'football_stats',
    'db_user' => 'root',
    'db_pass' => 'password'
];
// 初始化数据库连接
$db = new PDO(
    "mysql:host={$config['db_host']};dbname={$config['db_name']}",
    $config['db_user'],
    $config['db_pass']
);
// 初始化API和聚合器
$api = new SofaScoreAPI($config['api_key']);
$aggregator = new SofaScoreRatingAggregator();
$repository = new RatingRepository($db);
// 获取球员综合评分
function getPlayerCompositeRating($playerId) {
    global $api, $aggregator, $repository;
    // 检查缓存
    $cachedScore = $repository->getCachedCompositeRating($playerId);
    if ($cachedScore !== null) {
        return $cachedScore;
    }
    try {
        // 获取评分数据
        $ratingsData = $api->getPlayerRatings($playerId);
        // 计算综合评分
        $compositeRating = $aggregator->calculateCompositeRating($ratingsData);
        if ($compositeRating) {
            // 缓存计算结果
            $repository->cacheCompositeRating($playerId, $compositeRating['composite_score']);
        }
        return $compositeRating;
    } catch (Exception $e) {
        // 记录错误日志
        error_log("获取球员评分失败: " . $e->getMessage());
        return null;
    }
}
// 使用示例
$playerId = 12345;
$compositeRating = getPlayerCompositeRating($playerId);
if ($compositeRating) {
    echo "球员综合评分: " . $compositeRating['composite_score'] . "\n";
    echo "出场次数: " . $compositeRating['matches_played'] . "\n";
    echo "平均评分: " . $compositeRating['avg_rating'] . "\n";
    echo "稳定性: " . $compositeRating['consistency_score'] . "\n";
    echo "趋势: " . $compositeRating['trend_score'] . "\n";
} else {
    echo "无法获取评分数据\n";
}

数据库表结构

-- 球员评分表
CREATE TABLE player_ratings (
    id INT AUTO_INCREMENT PRIMARY KEY,
    player_id INT NOT NULL,
    team_id INT,
    event_id INT,
    rating DECIMAL(3,1),
    match_date DATE,
    UNIQUE KEY unique_player_match (player_id, event_id),
    INDEX idx_player_date (player_id, match_date)
);
-- 综合评分缓存表
CREATE TABLE player_composite_ratings (
    player_id INT PRIMARY KEY,
    composite_score DECIMAL(3,1),
    updated_at DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
    INDEX idx_updated (updated_at)
);
-- 球员信息表(可选)
CREATE TABLE players (
    id INT PRIMARY KEY,
    name VARCHAR(100),
    team_id INT,
    position VARCHAR(20),
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

注意事项

  1. API限制:SofaScore API有请求频率限制,建议使用缓存减少API调用
  2. 数据时效性:评分数据每场比赛后更新,建议定期同步
  3. 错误处理:API可能会返回错误或限流,需要有完善的错误处理机制
  4. 多维度评分:可以根据需要扩展评分维度(如位置权重、比赛重要性等)
  5. 前端显示:可以使用图表库(如Chart.js)展示评分趋势

这个方案提供了完整的SofaScore综合评分统计功能,可以根据实际需求进行调整和扩展。

抱歉,评论功能暂时关闭!