2011-06-16 74 views
7

我基本上为我创建的广告系统创建一个显示模块。避免使用面向对象设计的if语句,PHP

我试图避免以下结构,重复的if语句。

我的直觉告诉我有更聪明的方法来做到这一点,也许与多态?

<?php 

class Ad { 
    public $adState = 'active'; 
} 

class AdWriter { 
    public function displayAd(Ad $ad, $viewmode = 'visitor') { 
     if ($viewmode =='visitor') { 
      if ($adState == 'active') {} 

      else if ($adState == 'paused') {} 

      else if ($adState == 'inactive') {} 

     } 

     else if ($viewmode = 'owner') { 
      if ($adState == 'active') {} 

      else if ($adState == 'paused') {} 

      else if ($adState == 'inactive') {} 
     } 

     else if ($viewmode == 'administrator') { 
      if ($adState == 'active') {} 

      else if ($adState == 'paused') {} 

      else if ($adState == 'inactive') {} 
     } 
    } 
} 

?> 

回答

0

我在工作中潜入StackOverflow,所以没有时间写出所有可能性的详细答复。在viewmode

switch $viewmode { 
    case 'visitor': 
    your_code_here; 
    break; 
    case 'owner': 
    your_code_here; 
    break; 
    default: 
    will_run_if_nothing_above_matches; 
    break; 
} 
+2

他问了一个更聪明的方法,并且你展示了它。好。 :) – 2011-06-16 11:23:17

+2

这并没有真正消除任何东西,但?我仍然坚持不断地检查各州。 – Poyan 2011-06-16 11:26:14

+0

-1这与我将研究的ifs – Gordon 2011-06-16 11:34:39

4

您可以创建一个Factory (Pattern),使用开关,并创建一个特定Ad实现一个interface有一个简单的函数“显示:

但要“收拾”那些如果,你可以这样做' 例如。

伪例如:

class AdFactory { 

    public static function getAd($sType) { 
     switch($sType) { 
      case "AdOne": 
       return new AdOne(); 
      case "AdTwo": 
       return new AdTwo(); 
     } 
    } 
    throw new Exception("Unknown ad!"); 
} 

class AdOne implement AdInterface { 
    public function display() { 
     // All that AdOne does when displaying. 
    } 
} 

interface AdInterface { 
    public function display() { } 
} 

$oAd1 = AdFactory::getAd('typeOne'); 
$oAd1->display(); 

$oAd2 = AdFactory::getAd('typeTwo'); 
$oAd2->display(); 
+0

实际上是相同的;谢谢。 – Poyan 2011-06-16 11:27:14

3

强似$视图模式中,传递了一个对象,将封装逻辑此viewmore并调用它的方法,会做的工作。这样你就可以避免if语句的需要。

0
switch($viewmode){ 
    case "visitor": 
     switch($adstate){ 
      case "active": 
       //statement 
       break; 
      case "paused": 
      break; 
      case "inactive": 
      break; 
     } 
     break; 
    case "owner": 
     break; 
    case "administrator": 
     break; 
} 
0

this book的第8章中,您可以找到非常详细的问题答案。

总之:使用Composition或工厂。 (见Wesley van Opdorp的答案)。

此外,应避免使用字符串参数作为枚举: $viewmode = 'visitor'
有这样的说法,你将不得不在内存中保留这种说法的所有可能的值。或者查看功能代码来记住它们。这些值是字符串 - 错别字的好地方。此外,要更改特征中的值将非常困难,因为此方法的所有调用都将包含硬编码的字符串。
使用类常数:

class AdWriter { 
const view_mode_visitor = 1; 
... 

此外,$adState - 错误的代码,应该是$ AD->状态。但使用公共领域这也是不好的做法:)