You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用PHP函数从数据库读取数据并返回数组?附实现代码

嘿,我来帮你拆解这段PHP代码的合理性,以及可以优化的地方,让它更贴合生产环境的需求:

代码合理性分析

值得肯定的亮点

  • 你用了预处理语句(prepare + bind_param),这直接规避了SQL注入风险,是数据库操作里非常标准的安全实践,必须给你点个赞!
  • 还做了预处理语句的创建失败检查,并且抛出异常,这种主动暴露错误的方式比静默失败强太多,调试的时候能快速定位问题。
  • 执行查询后调用store_result()提前获取行数,用来判断是否有匹配结果,这个逻辑思路是通顺的。

存在的问题与优化建议

1. 返回类型不统一,调用方容易踩坑

当前代码里,没查到数据时返回字符串"...",但按照你的需求,正常情况应该返回数组。这种返回类型不一致的情况,会让调用这个函数的代码很容易出错——比如调用方本来想用foreach遍历结果,结果拿到字符串直接报错。

改进建议:没结果时返回空数组[],保持返回类型始终是数组,调用方处理起来更安全。

2. 缺失结果集读取逻辑,等于白查了

你的代码只做了查询、判断行数,但完全没写读取查询结果、组装成数组返回的逻辑——这会导致查到数据时,函数默认返回null,完全达不到你“从数据库读取值并返回数组”的需求。

这里给你两种常见的结果读取方式:

方式一:用get_result()(更简洁,需要PHP版本≥5.3.0且MySQL驱动支持)

public function avtorizacije($user) {
    $sql = "SELECT * FROM uporabniki_avtorizacije WHERE userId=?";
    if( !$this->stmt = $this->mysqli->prepare($sql) ) {
        throw new Exception("MySQL Prepare statement failed: ".$this->mysqli->error);
    }
    $this->stmt->bind_param("i", $user);
    // 新增执行结果检查
    if (!$this->stmt->execute()) {
        throw new Exception("MySQL Execute failed: ".$this->stmt->error);
    }
    // 获取结果集并转成关联数组
    $result = $this->stmt->get_result();
    $avtorizacije = $result->fetch_all(MYSQLI_ASSOC);
    
    $this->stmt->close(); // 显式关闭语句,释放资源
    return $avtorizacije; // 没结果时自动返回空数组
}

方式二:用bind_result()(兼容更低版本PHP)

public function avtorizacije($user) {
    // 建议明确指定字段,不要用SELECT *
    $sql = "SELECT id, permission, created_at FROM uporabniki_avtorizacije WHERE userId=?";
    if( !$this->stmt = $this->mysqli->prepare($sql) ) {
        throw new Exception("MySQL Prepare statement failed: ".$this->mysqli->error);
    }
    $this->stmt->bind_param("i", $user);
    $this->stmt->execute();
    // 绑定对应字段
    $this->stmt->bind_result($id, $permission, $createdAt);
    
    $avtorizacije = [];
    // 循环读取每一行结果
    while ($this->stmt->fetch()) {
        $avtorizacije[] = [
            'id' => $id,
            'permission' => $permission,
            'created_at' => $createdAt
        ];
    }
    
    $this->stmt->close();
    return $avtorizacije;
}

3. 建议显式释放资源

你的代码没有关闭预处理语句($this->stmt->close()),虽然PHP脚本结束后会自动回收资源,但显式关闭是更严谨的编程习惯,尤其是在长时间运行的脚本中,能避免不必要的资源占用。

4. 尽量别用SELECT *

建议明确写出需要查询的字段,而不是用SELECT *:

  • 减少不必要的数据传输,提升查询性能;
  • 避免后续表结构变更(比如新增/删除字段)导致的代码意外问题,让逻辑更健壮。

5. 补充执行阶段的错误检查

除了预处理创建失败,还可以对execute()的结果做检查,捕获执行阶段的错误(比如数据库权限不足、字段不存在等),让错误处理更全面。

额外的技术小建议

如果你的项目版本允许,推荐用PDO替代mysqli——PDO支持更多数据库类型,API更简洁,处理结果集也更方便(比如直接用fetchAll()),代码可读性和复用性都会更高。

内容的提问来源于stack exchange,提问作者zupko

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 06:51:28