3

如果我的产品是这样存储的:

tbl_products
id, price, stock
1, 20, 5
2, 30, 5

文本在另一张桌子上:

tbl_texts
id, item_id, type, field, value
1, 1, 'product', 'name', 'Programming Book'
2, 1, 'product', 'description', 'A fine book'
3, 2, 'product', 'name', 'Bicycle'
4, 2, 'product', 'description', 'Goes very fast'

活动价格也在另一张桌子上:

tbl_product_campaign_prices
id, item_id, price, valid_from, valid_to
1, 1, 5, null, null
2, 2, 10, null, 2014-10-10

好的,这是我的想象表。

我想将产品作为对象处理,因为我并不总是想要获取与产品相关的所有数据,因为它的数据库很重,我很少需要访问所有这些数据。

例如,有时我只需要产品的名称或描述。有时我需要竞选价格。将始终获取 tbl_products 上的基本信息。

真正的问题是;我对代码有什么选择。我想出了几个:

1.

$product_id = 1;
$fetch_name = 1;
$fetch_description = 0;
$fetch_campaign_prices = 0;
$product = ProductFactory::get($product_id, $fetch_name, $fetch_description,
           $fetch_campaign_prices);

// This takes a lot of space and is very impractical 
// when I have to add new data to be fetched.

// Worst case would be having to add a bunch 
// of null, null, null to get the last data.

2.

// Same as 1. but adding all the $fetch_ into an array and only use 2 parameters on the
// get() function.

$product = ProductFactory::get($product_id, $fetch_array);

// Still pretty ackward way to fetch data but much easier to add stuff 
// since I don't have to add any new parameters

3.

$data_to_fetch = array('name', 'description');
ProductFactory::Prepare($data_to_fetch);
$product = ProductFactory::get($product_id);

有没有一种通用的方法可以做到这一点?一种有效的方法来做到这一点?我从来没有做过这样的事情,这些都是我的想法。

感谢您即将到来的输入!

4

2 回答 2

0

基本上,您是在询问如何表达一小组配置标志的子集。这与您使用它的数据库几乎无关。

  1. 使用单独的参数:很难维护,一个地方的变化将需要所有地方的变化。但是,如果没有合理的默认值,这可能是有意义的。在这些情况下,呼叫失败可能比做错事要好。

  2. 使用有序的参数数组:非常难看,因为您必须记住顺序的含义,而且更难判断何时调用不正确。不要那样做。

  3. 名称列表:非常灵活且易于阅读。这可能是python的做事方式。但是检查包含哪些值,哪些不包含需要进行多次字符串比较,因此这可能有点昂贵。不过,可能不超过中等数据库查询。要考虑的一件事是是否检查被调用函数不知道的名称。您可以将这些报告为错误以避免拼写错误,或者您可以选择忽略它们以实现前向兼容性。

  4. 位掩码:正如 Mark Ba​​ker 指出的那样,您可以定义许多具有可读名称和值的常量,它们是 2 的幂。您可以或它们一起使用|以形成单个值。然后,您可以使用按位并从函数中的组合值中提取单个位。这是 C 做事的方式。它具有高性能,拼写错误的风险低。但它可能会用这些符号常量破坏你的命名空间。

  5. 配置对象:您可以为传递给该函数的参数定义一个类。您将有设置器来设置各种标志。最重要的是,您将拥有一个可以设置默认值的构造函数。所以这里的主要好处是你可以建立健全的默认值,即使有些东西应该被默认获取而其他东西不应该被获取,并且不需要调用像FETCH_FOOand这样的常量名称DONT_FETCH_BAR

我会去4。

于 2013-10-01T13:53:16.170 回答
0

首先,我假设这是一个假设的例子——但要小心你在性能和复杂性之间做出的权衡——你很可能会发现 PHP 代码中的额外复杂性成为一个维护问题。相反,您可能还会发现额外的 PHP 代码超过了不加载额外数据的好处。

其次,大多数对象关系映射框架解决这个问题的方式是通过“延迟加载”。ORM 只会在需要时从您的活动价格表中加载数据;这对开发人员来说大多是透明的。

当然,这不适用于您的“文本”表,它实际上是一个实体属性值存储。在这种情况下,这取决于您的文本模式的固定程度。如果您知道自己总是有“名称”和“描述”,则可以将其硬编码为位掩码。然而,这种设计往往会随着时间的推移而增长(否则,您最好在 products 表中使用“名称”和“描述”列)。在这种情况下,我会坚持将文本类型作为字符串参数传递——“名称”、“描述”。这意味着当您添加新的文本类型“shortDescription”时,您不必重新访问 productFactory 代码以使其知道新的文本类型。

于 2013-10-01T14:07:27.850 回答