2013-05-10 69 views
1

我使用的是CodeIgniter,但这个问题也适用于一般意义。PHP代码重复。在什么时候复制代码是正确的方式?

我的交易与

item_name | type | date | price | document 

我想做的事情在两个完全独立案件下面的表格。

1)获取特定日期范围内的交易清单。 2)获取某个日期范围内每个transaction.type的总价格。

前者可以通过简单地使用一个选择语句具有> datetimestamp

后者可以通过选择SUM,并且由类型而像实施任何所需的分组来实现来实现,其中条件句例如具有> datetimestamp

尽管这是一个简单的例子,但为了实现这一点,我需要两种方法,但是这两种方法(即WHERE子句)的大部分都在两种方法中重复使用。

在速度等方面它并不重要,但它似乎是无意义的代码复制。


第二个例子如下。

我先前在一个单独的方法有一个方法get_data($ID)这会从一个表中基于传入的ID获得的一行。

这样我会得到我的100个项目例如..返回一个数组,环通过它们并为每个调用get_data。

此设置意味着许多不同的方法可以从不同的来源获得不同的列表,然后仍使用相同的get_data函数和循环来获取所需的数据。

这最大限度地减少了代码重复,但却令人难以置信地不够高效,因为它意味着循环处理大量数据项和数百个数据库查询。

在我目前的设置中,我只是加入我的每个方法中的数据表 - 代码重复但明显提高了效率。


最后一个例子是如下

CI中我能有这样的功能,如下所示:

get_thing($ID) 
{ 
$this->load->database(); 
$this->db->where('ID',$ID); 
$this->db->get('table'); 
} 

,但在备选的情况下,我可能想只得到一个特定的项目文件夹..因此使功能更通用的作品更好..例如

get_thing($array) 
{ 
$this->load->database(); 
$this->db->where($array); 
$this->db->get('table'); 
} 

但我可能要在两个不同的上下文中使用此功能e.g用户页面和管理页面,从而管理员可以看到所有的项目,即使未经证实的。我的代码现在变为:

get_thing($array,$show_unverified = false) 
{ 
$this->load->database(); 
$this->db->where($array); 
if($show_unverified == false) 
{ 
$this->db->where('verified','YES'); 
} 
$this->db->get('table'); 
} 

正如你可能会看到这个可以很快失控和方法可以变得过于复杂,混乱,充满条件句。


我的问题是如下 - 什么是尽量减少重复代码的最佳实践,以及他们怎么可能被应用到上述情况?我花了好几个小时试图让我的代码更有效率,但是我无处可去,因为我无法锻炼我应该实现的目标。

干杯

+0

我完全同情!希望CodeIgniter(或其他框架)的专家能够解决这个问题。 – 2013-05-10 13:02:43

回答

0

我对数据库访问函数代码重复的想法是,它往往是更好地保持它分开。

我的规则特别是函数不应该返回不同类型的数据,这取决于参数,例如它不应该返回单个用户,有时也不会返回一个用户数组。它可能会返回错误代码(false)。

但是,如果函数实现不同的访问级别,这些访问级别可以在多个页面间共享。

0

这基本上总是回归常识。您应该尽量减少重复代码并尽量降低单一功能的复杂性。保持他们小而简单。

因此,基本上每次尝试推广这样的功能时,您都必须询问重复代码的问题是否大于过于复杂的功能问题。

在这种情况下,我会停在你的第二个点和未来,你可以创建最常见任务的一些包装(但要小心不要让包装的迷宫)

//you generic function 
function get_thing($array) 
{ 
$this->load->database(); 
$this->db->where($array); 
$this->db->get('table'); 
} 

// a nice and friendly wrapper 
function get_thing_by_id($id) 
{ 
    get_thing(array('id' => $id)); 
} 

// this is just getting silly. don't go crazy with wrappers, only for very often used things. 
// and yes the function name is purposely crazy ;) 
function get_thing_verified_by_name_and_city_and_some_more($name, $city, $somethingElse) 
{ 
    get_thing(array('name' => $name, 'city' => $city, 'somethingelse' => $somethingElse)); 
} 
0

这回答第一部分你的问题。假设你正在使用mysql_fetch_assoc或类似的。在迭代结果集时,您可以将循环中的变量中的计数值存储在每个事务类型的总价格中。

第二部分,只要你不重复代码,这会导致你维护代码库时的问题,这是没问题的。对于你的函数,你总是可以测试传递给函数的变量的类型,并相应地设置条件行为。

查看与软件设计模式相关的工厂模式或策略模式以进一步了解。

+0

嗯,是的,我可以,但在这种情况下,这个循环是否有10,000条记录要比使用SUM长得多? – 2013-05-10 13:25:23