1

私は一般的なコードベースを持つアプリケーションを設計していますが、その一部は特定のショッピングカートに非常に固有のものです。それに対応するように設計されたカートの数が増えるにつれて、メインクラスに追加するメソッドが増えています。これにより、クラスはかなり大きくなり、扱いにくくなっています。

メインクラスをロードする特定のカートごとに、カートのメーカーとバージョンが一致する場合にのみロードされる独自の特定のメソッドを持つように、モジュール化するにはどうすればよいですか?

たとえば、今このように設定しているとします。

class Thingy {
    public function doStuffMagento16() {...}
    public function getMoreMagento16() {...}
    public function doStuffOpencart15() {...}
    public function getMoreOpencart15() {...}
    public function doStuffPrestashop12() {...}
    public function getMorePrestashop12() {...}
    public function doStuffXcart45() {...}
    public function getMoreXcart45() {...}
}

メソッドがメインクラスのデフォルトをオーバーロードするように、どうすればこのように見せることができますか?

class Thingy {
    public function doStuff() {...}
    public function getMore() {...}
}

これを行うには、メインクラスを拡張し、メインインターフェイスが呼び出されたときにそれらを自動ロードする子クラスを作成する必要があると本当に思っていますが、これを試す前に、これが本当に最も効率的で保守しやすいオプションであることを確認したいと思います。 ....または別の方向に進む必要がある場合。

4

2 に答える 2

1

これには、アダプタパターンが必要です。特定のカートインターフェイスを汎用インターフェイスに適合させます。

簡単な例:

/* existing cart implementation */
class CartFromVendorX
{
    public function addProduct( CartXProduct $product ) {}
}

/* existing cart implementation */
class CartFromVendorY
{
    public function pushProduct( CartYProduct $product ) {}
}

/* generic cart interface */
interface CartAdapterInterface
{
    public function addItem( $item );
}

class CartAdapterVendorX
    implements CartAdapterInterface
{
    protected $adaptee;

    public function __construct( CartFromVendorX $adaptee )
    {
        $this->adaptee = $adaptee;
    }

    public function addItem( $item )
    {
        /* transfrom generic $item to CartXProduct, for instance */

        $this->adaptee->addProduct( $product );
    }
}

class CartAdapterVendorY
    implements CartAdapterInterface
{
    protected $adaptee;

    public function __construct( CartFromVendorY $adaptee )
    {
        $this->adaptee = $adaptee;
    }

    public function addItem( $item )
    {
        /* transfrom generic $item to CartYProduct, for instance */

        $this->adaptee->pushProduct( $product );
    }
}

次に、一般的なカートを消費するクライアント:

class CartClient
{
    protected $cart;

    public function __construct( CartAdapterInterface $cart )
    {
        $this->cart = $cart;
    }

    /* rest of implementation that acts on CartAdapterInterface instance */
}

使用法:

$cartAdapter = new CartAdapterVendorX( new CartFromVendorX() );
$client = new CartClient( $cartAdapter );

PS:元の実装をコンストラクターに渡すように、必ずしもアダプターを実装する必要はありません。このようなものも同様に機能する可能性があります。

class CartAdapterVendorX
    implements CartAdapterInterface
{
    protected $adaptee;

    public function __construct()
    {
        $this->adaptee = new CartFromVendorX();
    }

    public function addItem( $item )
    {
        /* perhaps transfrom generic $item first */

        $this->adaptee->addProduct( $item );
    }
}

次に、その使用法は次のように単純化されます。

$cartAdapter = new CartAdapterVendorX();
$client = new CartClient( $cartAdapter );

実際の実装の詳細はさまざまですが、これで一般的な考え方がわかります。たとえば、一部またはすべての元のカートに対して、ファサードパターンを実装する可能性が高くなります。これは、1つの元の実装に対する複数のメソッド呼び出しをアダプタインターフェイスの単一のメソッドにラップする場合があるためです。

于 2013-02-05T03:20:51.053 に答える
0

すべてのカートに共通することがわかっているすべてを含む基本クラスを作成します。

class Cart {

    function __construct(){

       $this->id = 1234;
       $this->item = 'basic_item';

    }

}

次に、クラスを別のクラスに拡張します。

class anotherCart extends Cart {

    function __construct(){

       $this->item = 'another_basic_item';

    }

}

この疑似例では、$this->id変数はとの両方で共通になりますがCartanotherCart変更するanotherCartと特別な扱いを受け$this->itemます。

追加の機能と条件を使用してこの概念を構築します。これにより、最も抽象的な概念でさえも簡単に使用できるようになります。

于 2013-02-05T03:01:09.947 に答える