Heim  >  Artikel  >  Backend-Entwicklung  >  Detaillierte Erläuterung des objektorientierten PHP-Interpretermodus

Detaillierte Erläuterung des objektorientierten PHP-Interpretermodus

墨辰丷
墨辰丷Original
2018-05-22 15:13:321345Durchsuche

Der folgende Editor bringt Ihnen ein Klischee über den objektorientierten Interpretermodus von PHP. Der Herausgeber findet es ziemlich gut, deshalb teile ich es jetzt mit Ihnen und gebe es als Referenz. Kommen Sie und schauen Sie sich den Editor an.

Nachdem ich den Inhalt des Buches studiert hatte, hatte ich sofort das Gefühl, etwas fortgeschritten zu sein. Ha! Tatsächlich ist es immer noch eine schlechte Idee. Ich glaube, dass es Anfängerfreunde geben wird, die dieses Buch lesen (ich bin auch ein Anfänger) und möchte meine Lernerfahrungen über den Inhalt des Buches teilen und austauschen, der meiner Meinung nach schwierig ist. 1. Ich hoffe, dass es das Wissen festigen kann Ich habe gelernt und die Rolle des vertieften Verständnisses 2. Ich hoffe, dass es für unerfahrene Freunde hilfreich sein wird, die diesen Artikel lesen und interessiert sind.

Ich habe diesen Teil mehrmals gelesen und den Code mehrmals eingegeben. Es wird geschätzt, dass die Funktion, die dieser Artikel erreichen möchte, darin besteht, dass der Benutzer einige Inhalte auf der Webseite eingibt und diese dann durch analysiert Hintergrundprogramm, um zu antworten (es fühlt sich an, als wäre das Unsinn). Wenn ich beispielsweise in das Eingabefeld der Frontend-Webseite Folgendes eingebe:

$input = "4";
$input equals "4" or $input equals "four";

und dann absende, antwortet das System mit einem Ergebnis ähnlich dem von „Bedingung ist wahr“ oder „Bedingung ist nicht wahr“ ( Es ähnelt in gewisser Weise dem Schreiben von Code direkt im Vordergrund und der Ausführung, und nach der Hintergrundanalyse wird ein Ergebnis zurückgegeben. Obwohl das Originalbuch nicht den gesamten Frontprozess erklärt -End-Eingabe für die Hintergrundanalyse, ich denke, diese Hintergrundanalyse sollte auch reguläre Ausdrücke verwenden, um etwas Ähnliches wie 2 oben zu extrahieren. Der Prozess von Schlüsselwörtern in Codezeilen)

Obwohl die beiden oben genannten Codezeilen Sprachen sind Vom Autor erfunden, ist es aufgrund der wörtlichen Bedeutung nicht schwer zu verstehen. Die erste Zeile definiert eine Variable und weist einen Wert zu, und die zweite Zeile führt eine Beurteilung durch (die Variable ist gleich 4 oder gleich vier). .

Werfen wir ohne weitere Umschweife einen Blick auf die durch dieses Muster definierten Klassen (bitte lesen Sie den Originaltext für Klassendiagramme selbst):

1. interpreterContext This Die Klasse ist wie ein Container , der hauptsächlich zum Speichern und Abrufen der zu vergleichenden Werte und Vergleichsergebnisse verwendet wird. Beispielsweise 4, 4 und das Vergleichsergebnis „wahr“ oder „falsch“. Der obige Code wird in Form eines Arrays gespeichert. Das heißt, das Attribut $expressionstore der Klasse lautet wie folgt:

class InterpreterContext{
  private $expressionstore = array(); //存放比较的值和结果
  
  function replace(Expression $exp,$value){    // 设置值
    $this->expressionstore[$exp->getKey()] = $value;
  }
  
  function lookup(Expression $exp){        //获取值
    return $this->expressionstore[$exp->getKey()];
  }
}

Diese Klasse ist wie ein Werkzeug, das von anderen Klassen verwendet werden kann (es erbt nicht von anderen Klassen, Kombinationen oder Aggregationen).

2. Ausdruck Dies ist eine abstrakte Ausdrucksklasse, die die abstrakte Methode interpret() und die Methode getKey()

The definiert Der Code lautet wie folgt:

abstract class Expression {
  private static $keycount = 0;  //计数用的
  private $key;          //存放一个唯一值


  //主要实现将前台获取到的数据存放到上述InterpreterContext类中的功能,看到下面的内容就会发现继承他的类调用了InterpreterContext类的replace()方法
  abstract function interpret (InterpreterContext $context); 

 //获取一个唯一值  
  function getKey(){       
    if(!isset($this->key)){
      self::$keycount++;
      $this->key= self::$keycount;
    }
    return $this->key;
  }
}

Die unten genannten Klassen erben alle diese Klasse und sie hat eine kombinierte Beziehung mit OperatorExpression (abstrakte Klasse für Operatorausdrücke). Das heißt, OperatorExpression kann alle Unterklassen einschließen, die Expression während der Initialisierung erben (dies ist auch der Schwerpunkt dieses Buches auf schnittstellenorientierter Programmierung). Dieser Ausdruck ist eine Schnittstelle. Mit dieser Schnittstelle kann Polymorphismus erreicht werden. Ich nicht Ich weiß, ob ich vorgebe, B zu sein. Ist das richtig? Details finden Sie im Klassendiagramm im Originalbuch.

3. LiteralExpression Literal Expression-Klasse, ihre Funktion ist Um eine Zeichenfolge im kleinen Container von InterpreterContext zu speichern, speichern Sie sie als Indexarray. Speichern Sie beispielsweise 4 oder 4 in den ersten beiden Sätzen des selbst erstellten Codes.

Der Code lautet wie folgt:

class LiteralExpression extends Expression{
  private $value;  
  function __construct ($value){      //初始化时传入要保存的值
    $this->value= $value;
  }
  function interpret(InterpreterContext $context){    //调用InterpreterContext类的replace()将$value保存到InterpreterContext这个小容器里
    $context->replace($this,$this->value);
  }
}

4. VariableExpression-Variablenausdrucksklasse, die dieselbe Funktion wie die obige Klasse hat, außer dass die Daten dies tun als assoziatives Array gespeichert werden. Der Schlüssel im assoziativen Array ist der Variablenname, und der Wert ist die Variable. Zum Beispiel die Variable „Eingabe“ und der Wert „4“ in den ersten beiden Sätzen,

Der Code lautet wie folgt:

class VariableExpression extends Expression{
  private $name;    //变量名
  private $val;      //变量值
  
  function __construct ($name,$val=null){
    $this->name = $name;
    $this->val = $val;
  }
  
  function interpret(InterpreterContext $context){
    if(!is_null($this->val)){
      $context->replace($this,$this->val);
      $this->val = null;
    }
  }
  
  function setValue($value){  //用于设置变量的值
    $this->val = $value;
  }
  
  function getKey(){    //这个复写了父类的getKey()方法,在小容器InterpreterContext的lookup()方法调用这个类的实例的getKey()方法时 它将返回一个字符串(即变量名)而不是数字索引
    return $this->name;
  }
}

5. Die abstrakte Basisklasse des OperatorExpression erbt und kombiniert die abstrakte Basisklasse „Ausdruck“. Die implementierte interpret()-Methode speichert hauptsächlich die Berechnungsergebnisse des Ausdrucks

Der Code lautet wie folgt:

abstract class OperatorExpression extends Expression{
protected $l_op;  //表达式左边的值
protected $r_op;  //表达式右边的值

function __construct (Expression $l_op,Expression $r_op){    //初始化时可组合继承了Expression类的子类实例
$this->l_op = $l_op;
$this->r_op = $r_op;
}

function interpret(InterpreterContext $context){  //主要用于保存表达试的结果(保存到InterpreterContext 类的实例中)
$this->l_op->interpret($context);        //将Expression子类实例的值或计算结果保存到InterpreterContext 类的实例中
$this->r_op->interpret($context);
$result_l = $context->lookup($this->l_op);    //获取上一步的值或计算结果
$result_r = $context->lookup($this->r_op);
$this->doInterpret($context,$result_l,$result_r);  //具体的比较运算由继承的子类来实现
}

protected abstract function doInterpret(InterpreterContext $context,$result_l,$result_r);

}

6. EqualsExpression, BooleanOrExpression bzw. BooleanAndExpression erben die abstrakte Basisklasse OperatorExpression. Es gibt intern nur eine Methode für gleiche Ausdrücke oder Ausdrücke ruft die Methode replace() der Klasse InterpreterContext auf, um das Berechnungsergebnis des Ausdrucks in einer Instanz der Klasse InterpreterContext zu speichern

Der Code lautet wie folgt:

//相等表达式
class EqualsExpression extends OperatorExpression {
protected function doInterpret(InterpreterContext $context,$result_l,$result_r){
$context->replace($this,$result_l == $result_r);
}
}

//或表达式
class BooleanOrExpression extends OperatorExpression{
protected function doInterpret(InterpreterContext $context,$result_l,$result_r){
$context->replace($this,$result_l || $result_r);
}
}


//与表达式
class BooleanAndExpression extends OperatorExpression{
protected function doInterpret(InterpreterContext $context,$result_l,$result_r){
$context->replace($this,$result_l && $result_r);
}
}

Die oben genannten Codes wurden bisher getestet und können direkt kopiert und eingefügt werden, um einen Blick darauf zu werfen am Kundencode:

Kundencode eins:

$context = new InterpreterContext();

$statement = new BooleanOrExpression (  //可尝试将此操作符表达式换成BooleanAndExpression 运行一下 看看执行结果

//可尝试将LiteralExpression中实例化的参数改成其他值看看运算结果,或者直接将EqualsExpression对象换成BooleanOrExpression 或BooleanAndExpression 
new EqualsExpression(new LiteralExpression('four'),new LiteralExpression('four')), 

new EqualsExpression(new LiteralExpression('b'),new LiteralExpression('4'))
);

$statement->interpret($context);
if($context->lookup($statement)){
echo '条件成立';
} else {
echo '条件不成立';
}

Client-Code zwei:

$context = new InterpreterContext();

$statement = new BooleanOrExpression(
new BooleanAndExpression(
new EqualsExpression(new LiteralExpression('4'),new LiteralExpression('4')),
new EqualsExpression(new LiteralExpression('4'),new LiteralExpression('4'))
),
new EqualsExpression(new LiteralExpression('b'),new LiteralExpression('4'))
);

$statement->interpret($context);
if($context->lookup($statement)){
echo '条件成立';
} else {
echo '条件不成立';
}

Client-Terminal-Code drei:

Der Unterschied zwischen diesem ursprünglichen Client-Codebeispiel und dem obigen Client-Code besteht in der Verwendung des Variablenausdrucks VariableExpression

$context = new InterpreterContext();    
$input = new VariableExpression('input');  //这里定义了一个变量input 但并未赋值

$statement = new BooleanOrExpression(
new EqualsExpression($input,new LiteralExpression('four')),  //这里变量表达式和文字表达式的值将进行一个是否相等的比较
new EqualsExpression($input,new LiteralExpression('4'))
);

foreach (array("four","4","52") as $val){
$input->setValue($val);        //对input这个变量赋值
print "变量input的值为:$val:<br/>";
$statement->interpret($context);  //进行比较并将比较结果存入InterpreterContext对象实例
if($context->lookup($statement)){  //获取比较的结果
print "条件成立 <br/>";
} else {
print "条件不成立 <br/>";
}
}

Der obige Code kann nach dem Testen normal ausgeführt werden. Bedürftige Freunde können ihn kopieren und ausführen, um die Ergebnisse anzuzeigen.

Verwandte Empfehlungen:

PHPInterpretermodusDetaillierte Verwendung

PHP-Designmuster Eingehende Analyse und detaillierte Erklärung des Interpreter-Musters

Erweitertes objektorientiertes PHP-Entwurfsmuster: Interpreter-MusterVerwendungsbeispiele

Das obige ist der detaillierte Inhalt vonDetaillierte Erläuterung des objektorientierten PHP-Interpretermodus. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn