2011-11-02 110 views
3

我正在尝试为不同货币如Euro,Doller等实现Currency货币类。 我试图创建一个抽象类并希望将Euro和Doller类从这个班。如何以更好的方式扩展这个抽象类

由于我是PHP新手,不知道这是否是更好的实现这种想法的方法。

abstract class Currency { 
     private $name; 
     private $symbol; 
     private $decimal; 
     private $decimal_point; 
     private $thousand_sep; 

     function __construct() {  
     } 

     function setName($name) { 
      $this->name = $name; 
     } 
     function getName() { 
      return $this->name; 
     } 

     function setSymbol($symbol) { 
      $this->symbol = $symbol; 
     } 
     function getSymbol() { 
      return $symbol; 
     } 

     function setDecimal($decimal) { 
      $this->decimal = $decimal; 
     } 
     function getDecimal() { 
      return $this->decimal; 
     } 

     function setDecimalPoint($decimal_point) { 
      $this->decimal_point = $decimal_point; 
     } 
     function getDecimalPoint() { 
      $this->decimal_point; 
     } 

     function setThousandSeprator($thousand_sep) { 
      $this->thousand_sep = $thousand_sep; 
     } 
     function getThousandSeprator() { 
      return $this->thousand_sep; 
     } 

     function display() { 
      return $this->symbol . number_format($this->amount, $this->decimal, $this->decimal_point, $this->thousand_sep); 
     } 
    } 
+0

只是一个提示:http://php.net/manual/en/class.numberformatter.php - 它是从国际图书馆这是开源的,你可以看看。 – hakre

回答

1

我不认为你需要所有那些setters,因为分隔符,小数点等在formatter生命期内不会改变。如果你希望你的班级做的是格式化货币,我认为你也不需要所有的获得者。

如果你的课只负责格式化,我认为你不应该把价值看作是一个班级领域;作为一个参数,最好把它传递给display()

怎么是这样的:

abstract class CurrencyFormatter { 
    protected $name; 
    protected $symbol; 
    protected $decimal; 
    protected $decimal_point; 
    protected $thousand_sep; 

    function format($amount) { 
     return $this->symbol . number_format($amount, $this->decimal, $this->decimal_point, $this->thousand_sep); 
    } 
} 

class EuroFormatter extends CurrencyFormatter { 
    public function __construct() { 
     $this->name = "Euro"; 
     $this->symbol = "E"; 
     $this->decimal = 2; 
     $this->decimal_point = "."; 
     $this->thousand_sep = ","; 

    } 
} 

然后,您可以使用它像这样:

$formattedAmount = new EuroFormatter()->format(123); 
1

使用抽象超类是有意义的,当你有一些功能,将由子类实现不同。例如,您希望以不同的方式显示欧元和美元,则可以定义display()函数摘要并使子类实现它。

abstract class Currency { 
.. 
.. 
abstract function display(); 
} 

class Dollar extends Currency { 
    function display() { 
     //display dollar 
    } 
} 

class Euro extends Currency { 
    function display() { 
     //display euro 
    } 
} 
2

你知道PHP5.3自带intl PECL捆绑在一起,从而知道哪些NumberFormatter应该能够做你想在这里建立的东西?

<?php 

$value = 9988776.65; 

$nf = new NumberFormatter('de_DE', NumberFormatter::CURRENCY); 
echo $nf->formatCurrency($value, "EUR") . "\n"; 
echo $nf->formatCurrency($value, "USD") . "\n"; 
$nf = new NumberFormatter('en_US', NumberFormatter::CURRENCY); 
echo $nf->formatCurrency($value, "EUR") . "\n"; 
echo $nf->formatCurrency($value, "USD") . "\n"; 
+1

由于以下原因,我强烈建议使用此解决方案:intl扩展依赖于来自CLDR存储库(http://cldr.unicode.org/translation/currency-names)的数据,该数据库是官方格式的集合(几乎)任何国家。而且:在您的类中包装和维护这些函数要容易得多,而不是为将来可能需要支持的每种货币编写PHP类。 – aurora

1

我会使用当前区域显示相关小数点,千个分隔符等,并只使用number_format()来显示它。

在英国,我们会说$12,345.67; €12,345.67£12,345.67
在法国,他们会说$12.345,67; €12.345,67£12.345,67
换句话说,格式不依赖于货币而是区域设置。

然而根抽象类货币是一个好主意 - 子类可能只需要覆盖$symbol,他们会做这样这样的:

abstract class Currency { 
    abstract private $symbol; 
/*...*/ 
} 

class GBP extends Currency { 
    private $symbol = "£"; 
} 

即没有必要的getter /这是因为它不会改变。

相关问题