Este artículo describe la implementación de Java para definir una función de lenguaje simple basada en el patrón de intérprete. Compártelo para su referencia, como sigue:
Una definición de patrón
Patrón de intérprete: es dar una representación gramatical de un idioma y definir un intérprete para interpretar las oraciones en el idioma. El patrón de intérprete describe cómo interpretar estas declaraciones utilizando el diseño de patrones después de una gramática simple.
Ejemplos del segundo modo
1 análisis de patrones
Diseñamos un idioma para ilustrar este patrón nosotros mismos
(1) El idioma es sensible a la caja (2) El idioma comienza con el programa y termina con el final (3) println significa imprimir una línea y romperla (4) usar para ... de ... a ... final medias significa bucle
El contenido del lenguaje de ejemplo es el siguiente:
Programa Println Inicio ... para I de 90 a 100 println I End Println End ... End
El significado de esta oración es: Primero imprima la línea de descanso con "Inicio ...", luego pase por la línea de descanso con "90", "91", ... "100", y finalmente imprima el descanso de la línea con "End ...".
2 Este idioma explica la estructura del árbol
3 Diagrama de actividad del intérprete del idioma
4 ejemplos de código
4.1 Crear un entorno de contexto - contexto
paquete com.demo.interpreter.context; import java.util.hashmap; import java.util.iterator; import java.util.map; import java.util.stringtokenizer;/** * entorno de contexto * * @author * */public class context {// El contenido de texto que se verá parselado de stringtekenizer privado finalizador; // El comando actual cadena privada actualtoken; // se usa para almacenar dinámicamente el contenido de información de contenido privado mapa final <string, object> map = new Hashmap <String, Object> (); / ** * El constructor establece el contenido de análisis * * @param text */ public context (texto de cadena) {// use espacios para separar el texto que se analizará. } / *** texto de análisis* / public String next () {if (this.stringTokenizer.hasMoretOkens ()) {currentToken = this.stringTokenizer.nextToken (); } else {currentToken = null; } return CurrentToken; } / ** * Determine si el comando es correcto * * @param command * @return * / public boolean igualwithCommand (comando de cadena) {if (command == null || } return verdadero; } / ** * Obtenga el contenido del comando actual * * @return * / public string getCurrentToken () {return this.currentToken; } / ** * Obtenga el contenido del nodo * * @return * / public String getTokEncontent (string text) {string str = text; if (str! = null) {// reemplazar el contenido de cambio dinámico en el mapa y return iterator <String> // Reemplace el contenido de cambio dinámico en el mapa y return iterator <String> iterator = this.map.keySet (). iterator (); while (iterator.hasnext ()) {string key = iterator.next (); Object obj = map.get (clave); str = str.replaceall (clave, obj.ToString ()); }} return str; } public void put (clave de cadena, valor de objeto) {this.map.put (clave, valor); } public void clare (tecla de cadena) {this.map.remove (clave); }}4.2 Interfaz de expresión: iExpresiones
paquete com.demo.interpreter.express; import com.demo.interpreter.context.context;/** * * interfaz de expresión * * @author * */public interfaz iExpressions {/** * analizador * * @param context */public void parse (contexto de contexto); / ** * Método de ejecución * * @param context */ public void interpret ();}4.3 Expresión principal - ProgramExpression
paquete com.demo.interpreter.express; import com.demo.interpreter.context.context;/** * Expression * * @author * */public class ProgrameExpression implementa IExpressions {// Contexty entorno de contexto final privado contexto final; // Comando actual Private Final Static String Command = "Program"; // Almacene las siguientes expresiones de referencia de referencia privada de Iexpressions; / ** * El constructor pasa el contenido para analizarse en * * @param text */ public programpression (texto de cadena) {this.context = new context (text); this.parse (this.context); } @Override public void Parse (contexto de contexto) {// Obtenga el primer nodo de comando this.context.next (); } / *** Método de explicación de implementación* / @Override public void interpret () {// Determine si comienza con el programa if (! This.context.equalswithCommand (comandante)) {System.out.println ("El '" + comando + "' está excepto para inicio!"); } else {// iniciar este.context.next () con el programa; this.expressions = new ListExpression (); this.expressions.parse (this.context); // La expresión de ListExpression comienza a analizar esto.expressions.interpret (); }}}4.4 Expresión de la lista - ListExpression
paquete com.demo.interpreter.express; import java.util.arrayList; import java.util.iterator; import com.demo.interpreter.context.context;/** * list Expression * * @author * */public class ListExpression implementa iExpressions {Contexto de contexto privado; ArrayList final privado <iExpressions> list = new ArrayList <Iexpressions> (); / ** * El constructor pasa el contexto a analizar * * @param context */ public void parse (contexto context) {this.context = context; // En la expresión de análisis de ListExpression, bucle para interpretar cada palabra en la declaración hasta que la expresión de terminador o excepción salga mientras (true) {if (this.context.getCurrentToken () == null) {// Obtener el nodo actual. Si es nulo, significa que a la expresión final le faltan sistemas.out.println ("Error: la experión que falta 'fin'!"); romper; } else if (this.context.equalswithCommand ("end")) {this.context.next (); // El análisis normalmente termina el ruptura; } else {// Crear expresión de comandos IExpressions expresiones = new CommandExpersion (this.context); // agregar a list.add (expresiones); }}} / *** Implementar el método de explicación* / @Override public void interpret () {// bucle la explicación de cada expresión en la lista de listas para ejecutar iterator <iExpressions> iterator = list.iterator (); while (iterator.hasnext ()) {(iterator.next ()). interpret (); }}}4.5 Expresión de comando - CommandExpersion
paquete com.demo.interpreter.express; import com.demo.interpreter.context.context;/** * Command Expression * * @author * */public class CommandExpersion implementa iExpressions {contexto final privado contextual; expresiones privadas de iExpressions; / ** * El método de construcción pasa el contexto para analizarse en * * @param context */ public CommandExpersSion (contexto context) {this.context = context; this.parse (this.context); } public void Parse (contexto de contexto) {// Juzgando la categoría de comando actual, solo distinga para y el comando original if (this.context.equalswithCommand ("for")) {// crea para expresión para analizar expresiones = new forexpression (this.context); } else {// Crear expresión de comando original para expresiones de análisis de contenido = new PrimitiveExpression (this.context); }} / *** Contenido de análisis* / @Override public void interpret () {// Contenido de análisis this.expressions.interpret (); }}4.6 Expresión de bucle - Forexpresión
paquete com.demo.interpreter.express; import com.demo.interpreter.context.context;/** * para expresión * * @author * */public class forexpression implementa iExpressions {contexto final privado contextual; // Almacene la variable de cadena privada del valor de clave de índice actual; // almacenar la posición de inicio del bucle privado int inicio_index; // almacenar la posición final del bucle private int end_index; expresiones privadas de iExpressions; / ** * El constructor pasa el contexto a analizar * * @param context */ public forexpression (contexto context) {this.context = context; this.parse (this.context); } / *** Expresión de análisis* / @Override public void Parse (contexto context) {// Primero obtenga el nodo actual este.context.next (); while (true) {// juzga el nodo if (this.context.equalswithCommand ("from")) {// establece la cadena de contenido de inicio nextStr = this.context.next (); intente {this.start_index = Integer.ParseInt (nextStr); } catch (Exception e) {System.out .println ("Error: después de 'de' Express Exist Error! Por favor, verifique el formato de expresión es correcto!"); romper; } // Obtenga el siguiente nodo this.context.next (); } else if (this.context.equalswithCommand ("to")) {// Establezca la cadena de contenido del índice final nextStr = this.context.next (); intente {this.end_index = Integer.ParseInt (nextStr); } catch (Exception e) {System.out .println ("Error: después de 'a' Express Exist Error! Por favor, verifique el formato de expresión es correcto!"); } this.context.next (); romper; } else {// Establezca el contenido de la variable de índice actual if (this.variable == null) {this.variable = this.context.getCurrentToken (); } // Obtenga el siguiente nodo this.context.next (); }} // Cree una expresión de lista this.expressions = new ListExpression (); this.expressions.parse (this.context); } / *** Implemente el método de explicación* / @Override public void interpret () {// Cree una expresión de comando para (int x = this.start_index; x <= this.end_index; x ++) {// Establezca el contenido variable this.context.put (""+this.variable, x); // ejecutar el método de explicación this.expressions.interpret (); } // Eliminar el contenido de la variable temporal utilizada this.context.clear ("" + this.variable); }}4.7 Expresiones básicas - PrimitiveExpression
paquete com.demo.interpreter.express; import com.demo.interpreter.context.context;/** * La expresión más básica * * @author * */public class primitiveExpression implementa iExpressions {contexto privado contexto; // Nombre del nodo String String Tokenname; // Texto de contenido de contenido privado Texto de cadena; / ** * El constructor pasa el contexto a analizarse en * * @param context */ public primitiveExpression (contexto context) {this.parse (context); } @Override public void parse (contexto context) {this.context = context; this.TokenName = this.context.getCurrentToken (); this.context.next (); if ("println" .equals (this.TokenName)) {this.text = this.context.getCurrentToken (); this.context.next (); }} / *** Método de explicación de implementación* / @Override public void interpret () {// Primero obtenga el contenido de nodo actual if ("println" .equals (tokenname)) {// Obtener información de contenido // Imprimir contenido System.out.println (this.context.gettokencontent (this.Text)); }}}4.8 Deje que el intérprete del idioma comience a funcionar - Cliente
paquete com.demo.interpreter; import com.demo.interpreter.express.iexpressions; import com.demo.interpreter.express.programexpression;/** * aplicación principal * * @author * */public class Client {/** * @param args */public estatic estatic bain (string [] args) {// Myida Starts st = " De 90 a 100 println I End Println End ... End "; System.out.println ("str:" + str); // Crear expresión del programa IExpressions expresiones = new ProgrameXpression (Str); // Explicar la ejecución de expresiones.interpret (); }}5 Resultados de ejecución
STR: Programa Println Start ... para I de 90 a 100 println I End Println End ... End
Comenzar...
90
91
92
93
94
95
96
97
98
99
100
fin...
Tres principios de diseño
Principio de 1 "cierre abierto"
2 El principio de cambio cerrado
Cuatro ocasiones de uso
(1) Un tipo específico de problema ocurre a alta frecuencia, y las reglas comerciales cambian con frecuencia, y situaciones similares ocurren repetidamente.
(2) Las reglas comerciales no son demasiado complicadas y engorrosas, y es más fácil abstraer reglas gramaticales.
(3) La eficiencia no es un factor principal considerado en los sistemas de software.
Cinco diagrama de clase estática en modo intérprete
Para obtener más contenido relacionado con Java, los lectores interesados en este sitio pueden ver los temas: "Introducción y tutorial avanzado sobre la programación orientada a objetos de Java", "Tutorial sobre la estructura de datos de Java y el algoritmo", "Resumen de la operación de Java DOM Node Node", "Summary of Java File and Directory Operation Skilly" y "Summary of Java Cache Skitch" Habilidades "
Espero que este artículo sea útil para la programación Java de todos.