如何处理对象集合?或者更确切地说,对象是否检索了类似对象的集合?

时间:2009-08-08 22:14:25

标签: php oop

我认为我在基本级别上获得了OOP范例,但我很难概念化在数据库中查找记录的正确方法。我怀疑这是因为我没有像我想的那样得到OOP ......

我正在尝试编写的应用程序是一个购物车,因为它有很多很好的候选对象。我将使用的对象是一个产品(是的,这是非常原始的)。

<?php
    class Product
    {
        public $id = 0;
        public $name = '';
        public $price = 0;

        function __construct($id)
        {
            // if $id exists try to retrieve
            // a product with $id
            // else create a new product
            // and set $this->id
        }
    }

    $product = new Product();
    echo $product->name;
?>

够容易。但现在我想查找多个产品(搜索结果页面),我不知道如何处理它。

我倾向于编写另一个类,它接受一些输入并执行只返回产品ID列表的SQL查询。然后我会遍历这些结果并为每个结果创建一个产品对象。然后我可以遍历对象数组并构建我的搜索结果页面。

我不确定为什么,但这只是感觉不对劲。似乎太多的工作,因为首先我正在进行查询以获取产品ID列表,然后我会进行更多查询以获取每个产品的数据。如果只做一个返回我需要的所有数据的查询,它会快得多。

做什么是正确的?还有别的吗?

4 个答案:

答案 0 :(得分:2)

编写一个不了解数据库的产品类(很难相信,但产品可以在没有数据库的情况下存在;))以及可以从数据库结果创建产品对象的类。 / p>

答案 1 :(得分:2)

从数据库到面向对象的应用程序的映射并非易事。有不同的方法可以解决这个问题,但一个简单的策略是拥有一个实体类(Product)和一个网关类(可以称为不同的东西,但通常是ProductGateway或ProductFinder)。网关类可以访问数据库,知道如何获取和初始化实体。同一个类也知道如何将对象映射回数据库。

例如:

class ProductGateway {
  function getProductById($id) {
    $result = $this->db->query("select * from products where id = ?", $id);
    return new Product($result->next());
  }
  function save($product) {
    if ($product->getId()) {
      return $this->update($product);
    } else {
      return $this->insert($product);
    }
  }
  ...
}

关键是您的应用程序级代码不需要知道产品是否来自数据库。它只是更改实体对象并将其留给网关来处理持久性。

答案 2 :(得分:0)

我认为你正在考虑正确的方法 - 但有一点,为什么只返回id,返回匹配产品的数组(或列表)。

具有查询方法的ProductFinder如何,参数是产品的定义,返回类型是产品的集合。

然后您可能会看到ProductFinder也可以负责创建产品(插入数据库),删除产品等。因此,产品本身对数据库知之甚少或根本不知道。然后,ProductFinder可能会得到一个稍微不同的名称,例如ProductKeeper或ProductHome。

如果除了产品之外你还有很多实体,那么你可能会发现他们的“守护者”有很多共同的代码,不久你最终会得到一个持久性框架。似乎有least one already的php,我建议你看一下。

答案 3 :(得分:0)

不要反过来使用现有的框架来处理OOP中的数据库。 Zend_Db具有不同的使用方法,最值得注意的是表网关/行网关方法,如上所述。 TableGateway旨在执行查询并返回行。行代表一行,可以独立操作。

如果您正在对许多行进行查询,则表示该表的单独类(或者在某些复杂连接的情况下甚至是“虚拟”表)是保持该表和个人关注点的最简洁方法行分开。