1

PHP (とりわけ) は、最も深い関数を最初に実行し、その方法を実行します。例えば、

$text = strtoupper(str_replace('_', ' ', file_get_contents('file.txt')));

テンプレートパーサーの上記の例と非常によく似たことをしています。タグを探します

{@tag_name}

$tag_nameという名前の変数に置き換えます。もう 1 つの例:

$a = 'hello';
$b = ' world';
INPUT = 'This is my test {@a{@b}} string.';
OUTPUT (step 1) = 'This is my test {@a} world string.';
OUTPUT output = 'This is my test hello world string.';

どうすればこれを行うことができますか?これは理にかなっていますか?そうでない場合は、より良い説明を試みることができます。

4

4 に答える 4

4

この例はネストの背後にある目的を示していないため、例のネストを理解しているかどうかはわかりません。入力例は非常に簡単です

'This is my test {@a} {@b} string.'

str_replace で配列を使用すると、これを非常に簡単かつ迅速に処理できます。

$aVars = array('{@a}' => 'hello', '{@b}' => 'world');
$sString = 'This is my test {@a} {@b} string.';

echo str_replace(array_keys($aVars), array_values($aVars), $sString);

それは私たちに与えます

これは私のテスト用の Hello World 文字列です。

さて、この再帰関数はそれほど難しくありませんが、それがどれほど役立つかはわかりません。これが実際の例です:

function template($sText, $aVars) {
    if (preg_match_all('/({@([^{}]+)})/',
                       $sText, $aMatches, PREG_SET_ORDER)) {
        foreach($aMatches as $aMatch) {
            echo '<pre>' . print_r($aMatches, 1) . '</pre>';

            if (array_key_exists($aMatch[2], $aVars)) {
                // replace the guy inside
                $sText = str_replace($aMatch[1], $aVars[$aMatch[2]], $sText);

                // now run through the text again since we have new variables
                $sText = template($sText, $aVars);
            }
        }
    }

    return $sText;
}

その print_r は一致がどのように見えるかを示すので、関数のペースをたどることができます。では、試してみましょう...

$aVars = array('a' => 'hello', 'b' => 'world');
$sStringOne = 'This is my test {@a} {@b} string.';
$sStringTwo = 'This is my test {@a{@b}} string.';

echo template($sStringOne, $aVars) . '<br />';

最初の結果:

これは私のテスト用の Hello World 文字列です。

では、弦 2 を試してみましょう

echo template($sStringTwo, $aVars) . '<br />';

2 番目の結果:

これは私のテスト {@aworld} 文字列です。

それはあなたが探しているものかもしれません。aworld明らかに、これが再帰的に機能するには変数が必要です...

$aVars = array('a' => '', 'b' => '2', 'a2' => 'hello world');

echo template($sStringTwo, $aVars) . '<br />';

そして私たちの結果。

これは私のテスト用の Hello World 文字列です。

そして、再帰を楽しむために...

$aVars = array('a3' => 'hello world', 'b2' => '3', 'c1' => '2', 'd' => '1');
$sStringTre = 'This is my test {@a{@b{@c{@d}}}} string.';

echo template($sStringTre, $aVars) . '<br />';

これは私のテスト用の Hello World 文字列です。

これがあなたが求めているものかどうかわからない...

于 2008-10-30T21:42:40.100 に答える
1

これは簡単な作業ではありません。文字列を手動で解析し、独自の論理置換を行う必要があります。これを行う魔法の関数や機能はありません。

私自身のテンプレート エンジンはそれ (およびそれ以上) を処理し、コア (テンプレート マクロなし) のみが 600+ LOC で重み付けされます。

于 2008-10-30T20:18:52.610 に答える
1

スタックを使用 -array_push開いている各要素を一番上に置きarray_pop、最初の終了マークで一番上に評価します。

于 2008-10-30T20:30:41.540 に答える
0

少なくともこの例では、@b トークンが @a トークンにネストされる理由がわかりません。二人はお互いを必要としていないようです。Perl でこのようなことをしようとしていますか?

$a = "b";
$b = "Hello World!";

print $$a;

出力は「Hello World」になります

于 2008-10-30T20:20:07.770 に答える