3

問題:

ArrayObjectは、値を手動で設定または読み取ると期待どおりに機能しますが、関数(foreachなど)を使用して反復処理すると、問題が発生します。

私が定義したoffset*メソッドを呼び出さず、代わりにArrayIteratorメソッドを使用します。

コード:

クラス:

class obsecureArray extends ArrayObject {


    public function offsetSet($name, $value) {
        call_user_func_array(array('parent', __FUNCTION__), array(base64_encode($name), base64_encode($value)) );
    }

    public function offsetGet($name) {
        return base64_decode( call_user_func_array(array('parent', __FUNCTION__), (array) base64_encode($name) ) );
    }

    public function offsetExists($name) {
        return call_user_func_array(array('parent', __FUNCTION__), (array) base64_encode($name) );
    }

    public function offsetUnset($name) {
        return call_user_func_array(array('parent', __FUNCTION__), (array) base64_encode($name) );
    }
}

使用例:

$a = new obsecureArray();
$a['test'] = 'Value';
$a[2] = '1';

define('BR','<br />');
echo 'test: ',$a['test'],BR,'2: ',$a[2],BR;

foreach($a as $key => $value)
    echo 'Key: ',$key,' Value:',$value,BR;

出力:

test: Value
2: 1
Key: dGVzdA== Value:VmFsdWU=
Key: Mg== Value:MQ==

CodePadの例。

4

4 に答える 4

3

ArrayObject __constructメソッドのドキュメントを調べたところ、問題に関連する3番目の引数が見つかりました。

iterator_class:

ArrayObjectオブジェクトの反復に使用されるクラスを指定します。ArrayIteratorは、使用されるデフォルトのクラスです。

ArrayIteratorこれで、独自のメソッドを使用してを拡張offset*し、のコンストラクターに渡すことができたArrayObjectので、調べたところ、明らかに外部イテレーターを使用していないことを除いてArrayIterator、ほとんど同じでした。ArrayObjectだから私がしなければならなかったのはArrayIterator代わりに拡張することだけでした。currentandkeyメソッドもオーバーライドする必要がありました。

だから私は持っています:

class obsecureArray extends ArrayIterator {

    public function offsetSet($name, $value) {
        call_user_func_array(array('parent', __FUNCTION__), array(base64_encode($name), base64_encode($value)));
    }

    public function offsetGet($name) {
        return base64_decode(call_user_func_array(array('parent', __FUNCTION__), (array) base64_encode($name)));
    }

    public function offsetExists($name) {
        return call_user_func_array(array('parent', __FUNCTION__), (array) base64_encode($name));
    }

    public function offsetUnset($name) {
        return call_user_func_array(array('parent', __FUNCTION__), (array) base64_encode($name));
    }

    public function key() {
        return base64_decode(parent::key());
    }

    public function current() {
        return base64_decode(parent::current());
    }



}

期待どおりに完全に機能します。

および:

$a = new obsecureArray();
$a['test'] = 'Value';
$a[2] = '1';

define('BR','<br />');
echo 'test: ',$a['test'],BR,'2: ',$a[2],BR;

foreach($a as $key => $value)
    echo 'Key: ',$key,' Value:',$value,BR;

私が得た:

テスト:値
2:1
キー:テスト値:値
キー:2値:1

CodePadの例

于 2012-01-11T05:08:11.877 に答える
1

IteratorまたはIteratorAggregateを実装する必要があります。前者をより細かく制御できますが、後者の方が実装が簡単です(おそらくオーバーヘッドが大きくなります)。

class People implements IteratorAggregate {
    protected $children;

    // ...

    public function getIterator() {
        return new ArrayIterator( $this->children );
    }
}

そのインターフェースの定型法については、イテレーターを参照してください。

于 2012-01-11T04:58:15.130 に答える
0

私の意見では、値が適切に処理されていることを確認したい場合は、コードが期待どおりに機能します。

$a = new obsecureArray();
$a->offsetSet('test', 'Value');
$a->offsetSet(2, '1');

またの代わりに

define('BR','
');

事前定義されたphpプロパティがありますPHP_EOL

于 2012-01-11T04:55:36.620 に答える
0

カスタムイテレータクラスを設定する必要があります。

<?php

class SecureArray extends ArrayObject {

    public function __construct($array = array()) {
        parent::__construct($array);
        $this->setIteratorClass('SecureIterator');
    }

    public function offsetSet($name, $value) {
        parent::offsetSet( base64_encode($name), base64_encode($value) );
    }

    public function offsetGet($name) {
        return base64_decode( parent::offsetGet( base64_encode($name) ) );
    }

    public function offsetExists($name) {
        return parent::offsetExists( base64_encode($name) );
    }

    public function offsetUnset($name) {
        return parent::offsetUnset( base64_encode($name) );
    }
}

class SecureIterator extends ArrayIterator {

    function current() {
        return base64_decode(parent::current());
    }

    function key() {
        return base64_decode(parent::key());
    }
}
于 2012-01-11T05:07:54.633 に答える