这个php项目显示人盯人防守成功率?

wen PHP项目 3

PHP项目实现"人盯人防守成功率"统计

我理解你想在PHP项目里显示人盯人防守成功率,下面给你一套完整的实现思路和代码示例,不过我需要先说明:你没有提供具体的项目代码/数据库结构,所以我给的是通用方案,你可以按自己的表结构对照修改。

这个php项目显示人盯人防守成功率?

核心公式

人盯人防守成功率 = 成功防守次数 / 防守总次数 × 100%

关键是:什么算"成功防守"?常见定义:

  • 对方持球人没有得分
  • 对方没有形成有效传球/突破
  • 对方投篮未命中且是你盯防的人

数据库设计(示例)

-- 防守事件记录表
CREATE TABLE defense_records (
    id INT AUTO_INCREMENT PRIMARY KEY,
    player_id INT NOT NULL COMMENT '防守球员ID',
    opponent_id INT NOT NULL COMMENT '被盯防的对手ID',
    match_id INT NOT NULL COMMENT '比赛ID',
    defense_type ENUM('man_to_man','zone') DEFAULT 'man_to_man' COMMENT '防守类型',
    is_success TINYINT(1) NOT NULL COMMENT '1=成功 0=失败',
    created_at DATETIME DEFAULT CURRENT_TIMESTAMP
);

计算成功率的PHP代码

方式1:PDO查询单个球员

<?php
function getManToManSuccessRate(PDO $pdo, int $playerId, ?int $matchId = null): array
{
    $sql = "SELECT 
                COUNT(*) AS total,
                SUM(is_success) AS success
            FROM defense_records
            WHERE player_id = :player_id
              AND defense_type = 'man_to_man'";
    $params = [':player_id' => $playerId];
    if ($matchId !== null) {
        $sql .= " AND match_id = :match_id";
        $params[':match_id'] = $matchId;
    }
    $stmt = $pdo->prepare($sql);
    $stmt->execute($params);
    $row = $stmt->fetch(PDO::FETCH_ASSOC);
    $total   = (int)($row['total'] ?? 0);
    $success = (int)($row['success'] ?? 0);
    $rate = $total > 0 ? round($success / $total * 100, 2) : 0.0;
    return [
        'total'   => $total,
        'success' => $success,
        'rate'    => $rate,   // 百分比数值,如 78.57
    ];
}
// 使用示例
$pdo = new PDO('mysql:host=localhost;dbname=your_db;charset=utf8mb4', 'user', 'pass');
$result = getManToManSuccessRate($pdo, 10);
echo "人盯人防守成功率: {$result['rate']}% ({$result['success']}/{$result['total']})";

方式2:一次性查全队(排行榜)

function getTeamManToManRates(PDO $pdo, int $matchId): array
{
    $sql = "SELECT 
                p.id,
                p.name,
                COUNT(d.id) AS total,
                SUM(d.is_success) AS success,
                ROUND(SUM(d.is_success) / COUNT(d.id) * 100, 2) AS rate
            FROM defense_records d
            JOIN players p ON p.id = d.player_id
            WHERE d.match_id = :match_id
              AND d.defense_type = 'man_to_man'
            GROUP BY p.id, p.name
            HAVING total > 0
            ORDER BY rate DESC";
    $stmt = $pdo->prepare($sql);
    $stmt->execute([':match_id' => $matchId]);
    return $stmt->fetchAll(PDO::FETCH_ASSOC);
}

在页面上显示(HTML模板)

<?php
$players = getTeamManToManRates($pdo, 1);
?>
<table border="1" cellpadding="8">
  <thead>
    <tr>
      <th>球员</th>
      <th>成功/总次数</th>
      <th>人盯人防守成功率</th>
    </tr>
  </thead>
  <tbody>
    <?php foreach ($players as $p): ?>
    <tr>
      <td><?= htmlspecialchars($p['name']) ?></td>
      <td><?= $p['success'] ?>/<?= $p['total'] ?></td>
      <td>
        <div style="background:#eee;width:120px;display:inline-block;vertical-align:middle;">
          <div style="width:<?= $p['rate'] ?>%;background:#28a745;color:#fff;text-align:center;">
            <?= $p['rate'] ?>%
          </div>
        </div>
      </td>
    </tr>
    <?php endforeach; ?>
  </tbody>
</table>

常见坑

问题 解决
除以0报错 先判断 total > 0
精度丢失 用 ROUND(...,2),或者SQL里用 SUM(x)/NULLIF(COUNT(*),0)
只看单场还是赛季 加 match_id 过滤参数
数据量大变慢 给 (player_id, defense_type) 加联合索引
区分主客/不同战术 defense_type 字段区分

需要你补充的信息

如果你想让代码直接能用在你的项目里,请告诉我:

  1. 你的数据库表结构(防守记录表字段有哪些?)
  2. "成功"的判定标准是什么?
  3. 是显示单个球员还是全队排行榜?
  4. 用的是 PDO / mysqli / 框架(ThinkPHP、Laravel),还是原生PHP?

把这些发给我,我可以直接帮你改成贴合项目的代码。

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