Sei sulla pagina 1di 17

Sintaxis para la construccin de archivos de gramtica para JavaCC

Los Tokens en los archivos de gramtica siguen las mismas convenciones que para el lenguaje de programacin Java. Por tanto identificadores, cadenas, caracteres, etc. Utilizada en las gramticas son iguales que los identificadores de Java, cadenas de Java, caracteres de Java, etc. Los espacios en blanco en los archivos de gramtica tambin siguen las mismas convenciones para el lenguaje de programacin Java. Este incluye la sintaxis para comentarios. La mayor parte de los comentarios presentes en los archivos de gramticas son generados dentro del analizador lxico/sintctico generado. Los archivos de gramtica son preprocesados por cdigos de escape Unicode tal como aparecen en los archivos Java (las ocurrencias de cadenas tales como \uxxxx donde xxxx es un valor hex son convertidos al carcter Unicode correspondiente antes de efectuar el anlisis lxico). Las excepciones a las reglas antes descritas: Los operadores de Java: "<<", ">>", ">>>", "<<=", ">>=", y ">>>=" son retiradas por la izquierda de la lista de tokens de entrada de JavaCC para permitir un uso conveniente de la especificacin de tokens. Finalmente, las siguientes son las palabras reservadas adicionales en los archivos de gramtica de JavaCC. EOF IGNORE_CASE JAVACODE LOOKAHEAD MORE options PARSER_BEGIN PARSER_END SKIP SPECIAL_TOKEN TOKEN TOKEN_MGR_DECLS Cualquier entidad de Java utilizada en las reglas de la gramtica que a continuacin aparezca con el prefijo java_ (Ej., java_compilation_unit). -------------------------------------------------------------------------------javacc_input ::= javacc_options "PARSER_BEGIN" "(" <IDENTIFIER> ")" java_compilation_unit "PARSER_END" "(" <IDENTIFIER> ")" ( production )* <EOF>

Los archivos de gramtica comienzan con una lista de opciones (las cuales son opcionales). Esto es entonces seguido por la unidad de compilacin de Java encerrado entre "PARSER_BEGIN(name)" y "PARSER_END(name)". Despues de esto hay una lista de producciones de la gramtica. Las opciones y producciones son descritas posteriormente. El nombre que sigue a "PARSER_BEGIN" y "PARSER_END" debe ser el mismo e identifica el nombre del parser generado. Por ejemplo, si el nombre es "MiParser", entonces se generan los siguientes archivos: MiParser.java: El analizador generado. MiParserTokenManager.java: El manejador de tokens generado (o analizador lxico).

MiParserConstants.java: Un conjunto de constantes tiles. Otros archivos como "Token.java", "ParseError.java", etc. Tambin son generados. Estos archivos contienen cdigo modelo y son el mismo para cualquier gramtica y pueden ser reutilizadas en otras gramticas. Entre las construcciones PARSER_BEGIN y PARSER_END se encuentra una unidad regular de compilacin de Java (una unidad de compilacin en java puede ser el contenido completo de un archivo en Java). Esto puede ser cualquier unidad de compilacin arbitraria tan grande como contenga una declaracin de clase y cuyo nombre sea el mismo que el nombre del parser generado ("MiParser" en el ejemplo anterior). Por tanto, en general, esta parte del archivo de la gramtica se vera como:
PARSER_BEGIN(parser_name) . . . clase parser_name . . . { . . . } . . . PARSER_END(parser_name)

JavaCC no realiza ninguna revisin detallada en la unidad de compilacin, as esto es posible para un archivo de gramtica pasar a travs de JavaCC y generar los archivos que producen errores cuando estos son compilados. Si la unidad de compilacin incluye un paquete de declaracin, esto es incluido en todos los archivos generados. Si la unidad de compilacin importa declaraciones, estas se incluyen en el parser generado y en los archivos del manejador de tokens. Si el archivo de parser generado contiene todo en la unida de compilacin y en adicin, contiene el cdigo generado del parser que se incluye al fin de la clase del parser. Para el ejemplo anterior, el parser generado se podra ver como sigue:
. . . clase parser_name . . . { . . . // El parser generado se incluye aqui. } . . .

Los parsers generados incluyen la declaracin de un mtodo pblico para cada noterminal (ver javacode_production y bnf_production) en el archivo de gramtica. El Anlisis Sintctico con respecto a un no-terminal se logra invocando el mtodo correspondiente a ese no-terminal. A diferencia de yacc, no hay ningn smbolo inicial en JavaCC uno puede iniciar el anlisis sintctico con respecto a cualquier no-terminal en la gramtica. El manejador de tokens provee un mtodo pblico:
Token getNextToken() throws ParseError;

Para ms detalles en como puede ser utilizado este mtodo, lea la documentacin de JavaCC.
javacc_options ::= [ "options" "{" ( option_binding )* "}" ]

Si la palabra options est presente, inicia con la palabra reservada options seguida de una lista de ms opciones encerradas con corchetes. Cada opcin encerrada especifica el establecimiento de una opcin. La misma opcin no debe ser indicada varias veces. Las opciones pueden ser especificadas tanto aqu en el archivo de gramtica o desde la lnea de comandos. Si la opcin se coloca desde la lnea de comandos, esta toma precedencia. Los nombres de opciones pueden ser maysculas o minsculas. -------------------------------------------------------------------------------option_binding ::= "LOOKAHEAD" "=" java_integer_literal ";" | "CHOICE_AMBIGUITY_CHECK" "=" java_integer_literal ";" | "OTHER_AMBIGUITY_CHECK" "=" java_integer_literal ";" | "STATIC" "=" java_boolean_literal ";" | "DEBUG_PARSER" "=" java_boolean_literal ";" | "DEBUG_LOOKAHEAD" "=" java_boolean_literal ";" | "DEBUG_TOKEN_MANAGER" "=" java_boolean_literal ";" | "OPTIMIZE_TOKEN_MANAGER" "=" java_boolean_literal ";" | "ERROR_REPORTING" "=" java_boolean_literal ";" | "JAVA_UNICODE_ESCAPE" "=" java_boolean_literal ";" | "UNICODE_INPUT" "=" java_boolean_literal ";" | "IGNORE_CASE" "=" java_boolean_literal ";" | "USER_TOKEN_MANAGER" "=" java_boolean_literal ";" | "USER_CHAR_STREAM" "=" java_boolean_literal ";" | "BUILD_PARSER" "=" java_boolean_literal ";" | "BUILD_TOKEN_MANAGER" "=" java_boolean_literal ";" | "TOKEN_MANAGER_USES_PARSER" "=" java_boolean_literal ";" | "SANITY_CHECK" "=" java_boolean_literal ";" | "FORCE_LA_CHECK" "=" java_boolean_literal ";" | "COMMON_TOKEN_ACTION" "=" java_boolean_literal ";" | "CACHE_TOKENS" "=" java_boolean_literal ";" | "OUTPUT_DIRECTORY" "=" java_string_literal ";"

LOOKAHEAD: El numero de tokens a observar por delante antes de tomar una decisin en un punto de opciones durante el Anlisis Sintctico. El valor por default es 1. Mientras ms pequeo sea dicho numero, el Anlisis ser ms rpido. Este nmero puede ser sobre-encimado por producciones especficas dentro de la gramtica como se describir posteriormente. Ver la descripcin del algoritmo lookahead para los detalles completos en como trabaja lookahead. CHOICE_AMBIGUITY_CHECK: Esta es una opcin entera la cual tiene un valor por default de 2. Este es el numero de tokens considerados en la revisin de ambigedad de opciones desde A|B. Por ejemplo, si hay dos prefijos de tokens comunes tanto para A y B, pero no hay tres tokens prefijos comunes, (asumiendo que esta opcin se pone a 3) entonces JavaCC puede informarte que debes usar un lookahead de 3 para propsitos

de eliminar la ambigedad. Y si A y B tienen tres tokens prefijos comunes, entonces JavaCC solo te dice que puedes necesitar tener un lookahead de 3 o ms. Al incrementar este valor te puede dar ms informacin respecto a la ambigedad al costo de ms tiempo de procesamiento. Para gramticas ms grandes como la gramtica de Java, incrementar este nmero mas all causa que la revisin tome mucho ms tiempo. OTHER_AMBIGUITY_CHECK: Esta es una opcin de un nmero entero el cual su valor por defecto es 1. Este es el numero de tokens considerados en la revisin de todos los otros tipos de opciones de ambigedad (ej. de las formas "(A)*", "(A)+", y "(A)?"). Esto toma ms tiempo en hacerse que revisar la opcin, y por tanto el valor por default es colocado en 1 ms bien que 2. STATIC: Esta es una opcin tipo lgica la cual su valor por default es verdadero. Si es verdadero, todos los mtodos y variables de clases son especificados como estticas en el analizador generado y el manejador de tokens. Esto solo permite que un objeto parser est presente, pero mejora el rendimiento del analizador. Para realizar varios analizadores durante una ejecucin del programa Java, tienes que invocar el mtodo ReInit() para reinicializar el parser si ste es esttico. Si el parser es no-static puedes utilizar el operador new para construir tantos parsers como necesites. Estos pueden ser utilizados simultneamente desde diferentes threads. DEBUG_PARSER: Esta es una opcin tipo lgica la cual establece un valor por default de falso. Esta opcin es utilizada para obtener informacin de depuracin desde los analizadores generados. Al establecer estas opciones en verdadero ocasiona que los parsers generen el seguimiento de sus acciones. El seguimiento puede ser deshabilitado invocando el mtodo disable_tracing() en la clase del parser generado. El seguimiento puede ser posteriormente habilitado al invocar el mtodo enable_tracing() en la clase del parser generado. DEBUG_LOOKAHEAD: Esta es una opcin tipo lgica la cual tiene un valor por default de falso. Al establecer esta opcin en verdadero (true) causa que el parser genere toda la informacin de seguimiento que se hace cuando se establece la opcin DEBUG_PARSER en verdadero, en adicin, esto tambin ocasiona que se genere la ruta de las acciones realizadas durante las operaciones de lookahead DEBUG_TOKEN_MANAGER: Esta es una opcin de tipo lgica la cual por default se establece en false. Esta opcin es utilizada para obtener informacin de depuracin desde el manejador de tokens. Al establecer esta opcin en true ocasiona que el manejador de tokens genere un seguimiento de sus acciones. Este seguimiento es bastante extenso y solo debe usarse cuando tengas un error lxico que haya sido reportado y no comprendas porque. Tpicamente, en esta situacin, puedes determinar el problema observando las ltimas cuantas lneas del seguimiento. ERROR_REPORTING: Esta es una opcin la cual tiene un valor por default de verdadero true. Si se establece en falso causar que los errores sean reportados con menos detalles. La nica razn para poner sta opcin en falso es mejorar su eficiencia. JAVA_UNICODE_ESCAPE: Esta es una opcin tipo lgica la cual tiene un valor por default de falso. Cuando se establece en true, el parser generado utiliza un objeto de flujo de entrada que procesa los cdigos de escape Unicode de Java (\u...) antes de

enviar los caracteres al manejador de tokens. Por default, los cdigos de escape Unicode de Java no son procesados. Esta opcin se ignora si cualquiera de las opciones USER_TOKEN_MANAGER, USER_CHAR_STREAM se establece en true. UNICODE_INPUT: Esta es una opcin tipo lgica la cual su valor por default es falso. Cuando se establece en true, el parser generado utiliza un objeto de flujo de entrada que lee los archivos Unicode. Por default se asume que los archivos son ASCII. Esta opcin se ignora si se establece en true cualquiera de las opciones USER_TOKEN_MANAGER, USER_CHAR_STREAM. IGNORE_CASE: Esta es una opcin de tipo lgica la cual el valor default es falso. Al poner esta opcin causa que el manejador de tokens generado ignore la diferencia entre maysculas y minsculas en la especificacin de tokens y los archivos de entrada. Esto es til para escribir gramticas para lenguajes tales como HTML. USER_TOKEN_MANAGER: Esta es una opcin tipo lgica la cual tiene por default el valor falso. La accin por default es generar un token manager que trabaja en aceptar tokens desde cualquier token manager de tipo TokenManager esta interfase es generada dentro del directorio del parser generado. USER_CHAR_STREAM: Esta es una opcin tipo lgica la cual por default se establece en falso. La accin por default es generar un lector de flujo de caracteres tal como se especifica en las opciones JAVA_UNICODE_ESCAPE y UNICODE_INPUT. El analizador lxico generado recibe los caracteres de este lector de flujo. Si esta opcin se establece en verdadero (true), entonces el analizador lxico generado para leer los caracteres desde cualquier lector de flujo de tipo "CharStream.java". El archivo es generado dentro del directorio del analizador sintctico generado Esta opcin se ignora si USER_TOKEN_MANAGER se establece en verdadero. BUILD_PARSER: Esta es una opcin de tipo lgica la cual tiene un valor por default de verdadero. La accin por default es generar el archivo de parser (("MiParser.java" en el ejemplo anterior). Cuando se establece en falso, el archivo del parser no es generado. Tpicamente esta opcin se pone en falso cuando solamente se desea generar el analizador lxico y utilizarlo sin el analizador lxico asociado (parser). BUILD_TOKEN_MANAGER: Esta es una opcin de tipo lgico la cual se establece por default al valor true. La accin por default es generar el archivo del Manejador de Tokens (Analizador lxico - "MiParserTokenManager.java" en el ejemplo anterior). Cuando se establece en falso el archivo del analizador lxico no se genera. La nica razn para colocar esta opcin en falso es ahorrar tiempo durante la generacin del analizador lxico cuando se arregla un problema en la parte de la gramtica del analizador y se deja las especificaciones sin modificacin alguna. TOKEN_MANAGER_USES_PARSER: Esta es una opcin de tipo lgico la cual tiene un valor por default de false. Cuando se establece en true, el manejador de token (analizador lxico) generado incluir un campo llamado parser que referenciar el objeto instanciado del Parser (de tipo MiParser en el ejemplo anterior). La principal razn de contar con una referencia al parser en un analizador lxico es el utilizar algunas de su lgica en las acciones lxicas. Esta opcin no tiene efecto si la opcin STATIC se establece en true.

SANITY_CHECK: Esta es una opcin lgica la cual su valor por default es true. JavaCC realiza muchas revisiones sintcticas y semnticas en el archivo de la gramtica durante la generacin del analizador sintctico. Algunas revisiones tales como la deteccin de recursividad por la izquierda, deteccin de ambigedad y mal uso de expansiones vacas pueden ser suprimidas para la generacin de un parser ms rpido al colocar sta opcin en falso. Note que la presencia de estos errores (aun cuando estas no son detectadas y reportadas al establecer sta opcin a Falso) pueden ocasionar un comportamiento inesperado desde el parser generado. FORCE_LA_CHECK: Esta es una opcin de tipo lgica la cual por default se encuentra en falso. Esta opcin controla la revisin de bsqueda adelantada de ambigedad que se realiza para todos los puntos de opcin donde se utiliza el valor por default de 1 para la bsqueda adelantada (o LookAhead) La bsqueda adelantada de ambigedad no se realiza en puntos de opcin donde hay una especificacin explcita de bsqueda adelantada, o si la opcin LOOKAHEAD se establece en otro valor distinto de 1. Al colocar esta opcin en true se realiza una bsqueda adelantada de ambigedad revisando todas las opciones a pesar de la especificacin de bsqueda adelantada en el archivo de la gramtica COMMON_TOKEN_ACTION: Esta es una opcin lgica la cual tiene el valor por default de falso. Cuando se establece en true, cada llamada al mtodo getNextToken del analizador lxico originara una llamada al mtodo "CommonTokenAction" despus de que el token ha sido reconocido por el analizador lxico. El usuario debe definir ste mtodo dentro de la seccin TOKEN_MGR_DECLS. El prototipo de ste mtodo es: void CommonTokenAction(Token t) CACHE_TOKENS: Esta es una opcin de valor lgico la cual por default es falso. Al establecer esta opcin en true ocasiona que el parser generado revise por tokens extra de forma anticipada. Esto facilita alguna mejora de eficiencia. Sin embargo, en este caso (cuando la opcin se establece en true), las aplicaciones interactivas podran no trabajar ya que el parser necesita trabajar en sincrona con la disponibilidad de tokens desde el flujo de entrada. En tales casos, es mejor dejar esta opcin con su valor por default. OUTPUT_DIRECTORY: Esta es una opcin para un valor de cadena de caracteres la cual el valor por default es el directorio actual. Esta opcin controla donde se generan los archivos de salida. -------------------------------------------------------------------------------production ::= | | | javacode_production regular_expr_production bnf_production token_manager_decls

Hay cuatro tipos de producciones en JavaCC. javacode_production y bnf_production son utilizadas para definir la gramtica desde la cual se genera el Parser. regular_expr_production se utiliza para definir la gramtica de tokens el token manager es generado a partir de sta informacin (tambin desde la especificacin de

tokens en lnea en la gramtica del parser). token_manager_decls se utiliza para introducir declaraciones que se insertan dentro del analizador lxico generado. -------------------------------------------------------------------------------javacode_production ::= "JAVACODE" java_access_modifier java_return_type java_identifier "(" java_parameter_list ")" java_block

La produccin JAVACODE es una manera de escribir cdigo Java para algunas producciones en lugar de utilizar la expansin usual EBNF. Esto es til cuando hay necesidad de reconocer algo en un contexto no libre o por cualquier otra razn que sea difcil para la cual sea difcil escribir una gramtica. Un ejemplo del uso de JAVACODE se muestra a continuacin. En ste ejemplo, el no terminal "skip_to_matching_brace" consume todos los tokens en el flujo de entrada hasta hacer coincidir con el corchete que cierra (se asume que el corchete izquierdo ya fue reconocido):
JAVACODE void skip_to_matching_brace() { Token tok; int nesting = 1; while (true) { tok = getToken(1); if (tok.kind == LBRACE) nesting++; if (tok.kind == RBRACE) { nesting--; if (nesting == 0) break; } tok = getNextToken(); } }

Se debe tener mucho cuidad en utilizar las producciones JAVACODE. Mientras que puedes decir bastante de lo que se desea con estas producciones, JavaCC simplemente las considera como una caja negra (algo que se realiza dentro de la tarea del anlisis). Esto puede ser un problema cuando las producciones JAVACODE aparecen en puntos de seleccin. Por ejemplo, si la produccin JAVACODE de arriba estuviera referenciada desde la siguiente produccin:
void NT() : {} { skip_to_matching_brace() | some_other_production() }

Entonces JavaCC no podra saber como escoger entre las dos opciones. De otra manera, si la produccin JAVACODE es utilizada en un punto que no hay opciones, como se muestra en el siguiente ejemplo, no habr problemas:

void NT() : {} { "{" skip_to_matching_brace() | "(" parameter_list() ")" }

Cuando las producciones JAVACODE son utilizadas en puntos de eleccin, JavaCC imprimir un mensaje de advertencia. Tendrs entonces que insertar algunas especificaciones explcitas LOOKAHEAD para ayudar al JavaCC. El modificador por default para produccin JAVACODE es un paquete privado. -------------------------------------------------------------------------------bnf_production ::= java_access_modifier java_return_type java_identifier "(" java_parameter_list ")" ":" java_block "{" expansion_choices "}"

La produccin BNF es la produccin estndar utilizada en la especificacin de gramticas JavaCC. Cada produccin BNF tiene un lado izquierdo el cual es una especificacin no-terminal. La produccin BNF entonces define este no-terminal en trminos de expansiones BNF en el lado derecho. El no-terminal es escrito exactamente como la declaracin de un mtodo en Java. Dado que cada no-termina es traducido dentro de un mtodo en el analizador generado, este estilo de escribir el no-terminal hace obvia esta asociacin. El nombre del no-terminal es el nombre del mtodo, y los parmetros y valores de retorno declarados son los medios para pasar los valores hacia arriba y abajo en el rbol sintctico. Tal como se ver posteriormente, el paso de valores hacia arriba y abajo del rbol se realiza utilizando exactamente el mismo paradigma que la invocacin y retorno a mtodos. El modificador de acceso para las producciones BNF es public. Hay dos partes en el lado derecho de la produccin BNF. La primer parte es el conjunto arbitrario de declaraciones de Java y cdigo (el bloque Java). Este cdigo es generado al inicio del mtodo generado por el no-terminal Java. Por tanto, cada vez que se utilice este no-terminal en el proceso de anlisis sintctico, estas declaraciones y cdigo son ejecutados. Las declaraciones en esta parte son visibles para todo el cdigo Java en las acciones en las expansiones BNF. JavaCC no realiza cualquier procesamiento de estas declaraciones y cdigo, excepto el salto hasta el corchete final, colectando todo el texto encontrado en el camino. Por tanto el compilador de Java puede detectar los errores en este cdigo que ha sido procesado por JavaCC. La segunda parte del lado derecho est en formato de expansin BNF. Esta se describe posteriormente. -------------------------------------------------------------------------------regular_expr_production ::= [ lexical_state_list ] regexpr_kind [ "[" "IGNORE_CASE" "]" ] ":"

"{" regexpr_spec ( "|" regexpr_spec )* "}"

Una produccin de expresin regular se utiliza para definir entidades lxicas a ser procesadas por el manejador de tokens. Esta seccin describe los aspectos sintcticos de la especificacin de entidades lxicas. Una produccin de expresin regular comienza con una especificacin del l estado lxico para las cuales aplica (la lista de estados lxicos). Hay un estado lxico estndar llamado DEFAULT. Si se omite la lista de estados lxicos, las producciones de expresin regular aplican el estado lxico "DEFAULT". Siguiendo esto es una descripcin de que tipo de produccin de expresin regular que es. Despues de esto hay un "[IGNORE_CASE]" opcional. Si esta presente, la produccin de expresin regular no distingue de maysculas y minsculas que es el mismo efecto que la opcin IGNORE_CASE, excepto que en este caso aplica localmente a esta produccin de expresin regular. Esto es entonces seguido por la especificacin de una lista de expresiones que describen con ms detalle las entidades lxicas de esta produccin de expresin regular. -------------------------------------------------------------------------------token_manager_decls ::= "TOKEN_MGR_DECLS" ":" java_block Las declaraciones del manejador de tokens comienza con la palabra reservada "TOKEN_MGR_DECLS" seguida por ":" y entonces un conjunto de declaraciones y sentencias Java (el bloque Java). Estas declaraciones y sentencias estn escritas dentro del manejador de tokens y estn accesibles desde las acciones lxicas. Solo puede haber una declaracin de manejador de tokens en una declaracin en un archivo de gramticas de JavaCC. -------------------------------------------------------------------------------lexical_state_list ::= "<" "*" ">" | "<" java_identifier ( "," java_identifier )* ">"

La lista de estados lxicos describe el conjunto de estados lxicos para los cuales corresponda la aplicacin de una produccin de expresin regular. Si esta escrita "<*>", la produccin de la expresin regular aplica a todos los estados lxicos. De otra forma, este aplica a todos los estados lxicos en la lista de identificadores dentro de los parntesis angulares.

-------------------------------------------------------------------------------regexpr_kind ::= "TOKEN"

| "SPECIAL_TOKEN" | "SKIP" | "MORE" Este especifica el tipo de produccin de expresin regula. Existen cuatro tipos: TOKEN: La expresin regular en esta produccin de expresin regular describe los componentes lxicos (tokens) en la gramtica. El manejador de tokens (analizador lxico) crea un objeto Token para cada coincidencia de cada expresin regular y la retorna al analizador sintctico. SPECIAL_TOKEN: La expresin regular en esta produccin de expresin regular describe tokens especiales. Los tokens especiales son como los tokens normales, excepto que no tienen significado durante el anlisis sintctico tal que las producciones BNF las ignoran. Los tokens especiales son pasados al parser enlazndolos a los tokens vecinos reales utilizando el campo specialToken en la clase Token. Los tokens especiales son tiles en el procesamiento de entidades lxicas tales como comentarios en los cuales no se realizar un anlisis significativo, pero son una parte importante del archivo de entrada. SKIP: Las coincidencias a una expresin regular en sta produccin de expresin regular son simplemente ignoradas por el manejador de tokens (Analizador lxico). MORE: Algunas veces es til construir gradualmente un token a ser pasado al parser. Las coincidencias de este tipo de expresiones regulares son almacenadas en un buffer hasta que coincida con TOKEN o SPECIAL_TOKEN. Entonces todas las coincidencias encontradas en el buffer y las coincidencias TOKEN/SPECIAL_TOKEN son concatenadas en la forma TOKEN/SPECIAL_TOKEN que es pasada al analizador sintctico. Si a una coincidencia a la expresin regular SKIP sigue una secuencia de coincidencias de tipo MORE, el contenido del buffer se descarta. -------------------------------------------------------------------------------regexpr_spec ::= regular_expression [ java_block ] [ ":" java_identifier ] La especificacin de expresiones regulares inicia la descripcin actual de las entidades lxicas que son parte de la produccin de la expresin regular. Cada produccin de expresin regular puede contener cualquier nmero de especificaciones de expresiones regulares. Cada especificacin de expresin regular contiene una expresin regular seguida de un bloque de Java (accin lxica) la cual es opcional. Esta es entonces seguida de un identificador de un estado lgico (la cual es opcional). Donde quiera que coincida sta

expresin regular, la accin lxica (si la hay) se ejecuta, seguida por cualquier cantidad de acciones comunes de los tokens. Entonces la accin depende del tipo de produccin de la expresin regular seleccionada. Finalmente, si se especifica un estado lxico, el manejador de tokens (analizador lxico), se mueve a ese estado lxico para futuro procesamiento (el analizador lxico inicia con el estado DEFAULT). -------------------------------------------------------------------------------expansion_choices ::= expansion ( "|" expansion )* Las selecciones de expansin se escriben como un alista de una o ms expansiones separadas por "|"s. El conjunto de analizadores legales seguidos por una seleccin de expansin es un anlisis legal de cualquier de las expansiones contenidas. -------------------------------------------------------------------------------expansion ::= ( expansion_unit )*

Una expansin esta escrita como una secuencia de unidades de expansion. La concatenacin de unidades de expansin correctamente analizadas es una expansin de analizador sintctico correcto. Por ejemplo, la expansin "{" decls() "}" consiste de tres unidades de expansin - "{", decls(), y "}". Una coincidencia para la expansin es una concatenacin de las coincidencias individuales de las unidades de expansin en este caso, que podra ser una cadena que inicie con {, termine con } y contenga una coincidencia intermedia para decls() -------------------------------------------------------------------------------expansion_unit ::= local_lookahead | java_block | "(" expansion_choices ")" [ "+" | "*" | "?" ] | "[" expansion_choices "]" | [ java_assignment_lhs "=" ] regular_expression | [java_assignment_lhs "="] java_identifier "(" java_expression_list")"

Una unidad de expansin puede ser una especificacin local LOOKAHEAD. Esto instruye al parser generado en como tomar las decisiones en los puntos de opciones. Una unidad de expansion puede ser un conjunto de declaraciones de Java y cdigo encerrado entre corchetes (bloque Java). Estas tambin se denominan acciones del analizador sintctico. Este es generado dentro del mtodo de anlisis del no-terminal en el lugar apropiado. Este bloque se ejecuta cada vez que el proceso de anlisis cruza este punto de forma exitosa. Cuando JavaCC procesa el bloque en Java, este no realiza ninguna revisin de la sintaxis o semntica. Por lo tanto es posible que el compilador de

Java pueda encontrar errores en las acciones que han sido procesadas por JavaCC. Las acciones no se ejecutan durante la evaluacin de adelantada de tokens. Una unidad de expansin puede ser un conjunto de una o ms opciones entre parntesis. En cuyo caso, un anlisis vlido de una unidad de expansin es cualquier anlisis legal de las expresiones anidadas. El conjunto de opciones de expansin entre parntesis puede ser opcionalmente acompaada a su derecha por: "+": Aqu cualquier coincidencia valida de la unidad es una o ms repeticiones de la coincidencia valida del conjunto de opciones entre parntesis. "*": Aqu cualquier coincidencia valida de la unidad es cero o ms repeticiones de una coincidencia valida del conjunto de opciones entre parntesis. "?": Aqu cualquier coincidencia valida de la unidad es tanto la cadena vaca como cualquier coincidencia valida de las opciones anidadas. Una sintaxis alterna para esta construccin es para encerrar las opciones de expansin dentro de los parntesis rectangulares "[...]". Una unidad de expresin puede ser una expresin regular. Entonces un anlisis vlido de la unidad de expansin es cualquier token que coincide esta expresin regular. Cuando coincide una expresin regular, este crea un objeto de tipo Token. Este objeto puede ser accesado asignndolo a una variable con el prefijo de la expresin regular con "variable =". En general, puedes tener cualquier asignacin valida de Java en el lado izquierdo del signo de igual "=". Esta asignacin no se realiza durante la evaluacin de la bsqueda anticipada (lookahead). Una unidad de expansin puede ser un no-terminal (la ltima opcin en la sintaxis descrita anteriormente). En cuyo caso, toma la forma de una invocacin a un mtodo con el nombre del no-terminal utilizado como el nombre del mtodo. Un anlisis exitoso del no-terminal origina que los parmetros colocados en la llamada del mtodo sean empleados para las operaciones y retornados sus valores (en el caso de que un noterminal no sea declarado del tipo void). El valor retornado puede ser asignado (opcionalmente) a una variable colocando como prefijo de la expresin regular con variable=. En general, puedes colocar cualquier asignacin valida de Java del lado izquierdo del signo =. Esta asignacin no se efecta durante la evaluacin adelantada de tokens. Los no-terminales no deben ser utilizados en una expansin de manera tal que introduzca una recursin por la izquierda. JavaCC realiza esta revisin. -------------------------------------------------------------------------------local_lookahead ::= "LOOKAHEAD" "(" [ java_integer_literal ] [ "," ] [ expansion_choices ] [ "," ] [ "{" java_expression "}" ] ")"

Una especificacin local de bsqueda anticipada de tokens (lookahead) se utiliza para influenciar la manera en que el analizador sintctico hace sus elecciones en varios puntos de opciones en la gramtica. Una especificacin local lookahead inicia con la palabra reservada "LOOKAHEAD" seguido por un conjunto de restricciones de lookahead entre parntesis. Hay tres tipos de restricciones un lmite de lookahead, un lookahead sintctico (eleccin de expansiones) y un lookahead semntico (la expresin

entre parntesis). Al menos debe estar presente una restriccin de lookahead. Si est presente ms de una restriccin lookahead, estas deben ser separadas por comas. A continuacin se proporciona una breve descripcin de cada tipo de restriccin del algoritmo LookAhead: Lookahead Limit (Limite LookAhead): Este es el mximo nmero de tokens (componentes lxicos) de bsqueda adelantada que pueden ser utilizados para propsitos de determinacin de seleccin de opciones. Esto sobre-escribe el valor por default el cual se especifica por la opcin LOOKAHEAD. Este limite lookahead aplica solo al punto de seleccin de opcin de la especificacin local de lookahead. Si la especificacin local de lookahead no esta en ste punto de seleccin, el limite de lookahead (si lo hay) es ignorado. Syntactic Lookahead: Esta es una expansin (o expansin de opciones) que se utiliza con el propsito de determinar si tiene que ser tomada o no una seleccin particular que aplica a esta especificacin local de lookahead. Si no se provee esto, el parser utilizar la expansin a ser seleccionada durante la determinacin lookahead. Si la especificacin local de lookahead no est en un punto de seleccin, la bsqueda sintctica anticipada (si la hay) es ignorada. Semantic Lookahead: Esta es una expresin de tipo lgica que se evala cuando el parser cruza este punto durante el anlisis sintctico. Si la expresin se evala a verdadero, el anlisis sintctico contina normalmente. Si la expresin se evala como falso y la especificacin local de lookahead se encuentra en un punto de eleccin, la opcin actual no se toma y se considera la siguiente opcin. Si la expresin se evala con falso y la especificacin local de bsqueda anticipado no se encuentra en un punto de eleccin, entonces se aborta el anlisis sintctico con un error de tipo Sintctico. A diferencia de las otras dos restricciones de lookahead que son ignoradas en puntos que no tienen opciones, el lookahead semntico siempre es evaluado. En efecto, el lookahead semntico es evaluado aun si esta se encuentra durante la evaluacin de alguna otra evaluacin sintctica. El valor default para las restricciones lookahead: Si fue provista una especificacin local de lookahead, pero no se incluyeron todas las restricciones lookahead, entonces las que fueron omitidas se asignan con los valores que se indica a continuacin: Si el lmite de lookahead no fue provisto y se provee un lookahead sintctico, entonces el lmite de lookahead se pone por default al valor entero ms grande (2147483647). Esto esencialmente implementa lo que se conoce como lookahead infinito esto es buscar de forma adelantada todos los tokens que sean necesarios para hacer coincidir el lookahead sintctico que se haya establecido. Si no se ha provisto de un limite de lookahead o un lookahead sintctico, el valor limite de lookahead por default es 0. Esto significa que no se realizar un lookahead sintctico, y solo se realizar un lookahead semntico. Si no se provee de un lookahead sintctico, se hace default la seleccin en la cual se aplica la especificacin lookahead local. Si la especificacin lookahead

no est en un punto de eleccin, entonces se ignora el lookahead sintctico por tanto el valor por default no es relevante. Si no se provee de una bsqueda anticipada de la semntica, este se aplica con la expresin lgica "true". -------------------------------------------------------------------------------regular_expression ::= java_string_literal | "<" [ [ "#" ] java_identifier ":" ] complex_regular_expression_choices ">" | "<" java_identifier ">" | "<" "EOF" ">"

Hay dos lugares en el archivo de la gramtica en la cual se pueden escribir expresiones regulares: Dentro de la especificacin de una expresin regular (parte de una produccin de una expresin regular), Como una unidad de expansin con una expansin. Cuando una expresin regular se utiliza de sta manera, esto es como si la expresin regular estuviera definida en la siguiente manera en sta localidad y entonces referenciada por su etiqueta desde la unidad de expansin:
<DEFAULT> TOKEN : { Expresin regular }

Esto es, el uso de expresiones regulares puede ser re-escritas utilizando otro tipo de forma. La descripcin de la construccin sintctica sigue a continuacin. El primer tipo de expresin regular es una cadena de caracteres literal. La entrada a ser analizada coincide con la expresin regular si el manejador de tokens esta en un estado lxico por el cual esta expresin regular aplica y el siguiente conjunto de caracteres en el flujo de entradas es el mismo (posiblemente se ignore la diferencia entre maysculas y minsculas) como esta literal de cadena de caracteres. Una expresin regular puede tambin ser una expresin regular compleja utilizando mas expresiones regulares relacionadas (mas que la definicin de la cadena de caracteres). Tal expresin regular es colocada dentro de parntesis angulares "<...>", y opcionalmente puede ser etiquetada con un identificador. Esta etiqueta puede ser utilizada para referir a esta expresin regular desde unidades de expansin o desde otras expresiones regulares. Si la etiqueta es precedida por el smbolo #, entonces esta expresin regular no puede ser referenciada desde unidades de expansin y solo desde otras expresiones regulares. Cuando esta presente el smbolo #, las expresiones regulares son referenciadas como expresiones regulares privadas

Una expresin regular puede referenciar a otras expresiones regulares etiquetadas, en cuyo caso est escrita como la etiqueta encerrada entre parntesis angulares "<...>". Finalmente, una expresin regular puede ser una referencia a una expresin regular predefinida "<EOF>" la cual es la coincidencia con el fin del archivo. Las expresiones regulares privadas no son hechas coincidir como tokens por el manejador de tokens (analizador lxico). Su propsito solamente es para facilitar la definicin de otras expresiones regulares ms complejas. Considere el siguiente ejemplo de definicin de las literales de nmeros flotantes en Java:
TOKEN : { < FLOATING_POINT_LITERAL: (["0"-"9"])+ "." (["0"-"9"])* (<EXPONENT>)? (["f","F","d","D"])? | "." (["0"-"9"])+ (<EXPONENT>)? (["f","F","d","D"])? | (["0"-"9"])+ <EXPONENT> (["f","F","d","D"])? | (["0"-"9"])+ (<EXPONENT>)? ["f","F","d","D"] > | < #EXPONENT: ["e","E"] (["+","-"])? (["0"-"9"])+ > }

En este ejemplo, el token FLOATING_POINT_LITERAL es definido utilizando la definicin de otro token llamado EXPONENT. El smbolo "#" previo a la etiqueta que este existe solamente para propsito de definir otros tokens (FLOATING_POINT_LITERAL en este caso). La definicin de FLOATING_POINT_LITERAL no es afectado por la presencia o ausencia de "#". Sin embargo, el comportamiento del manejador de tokens es: si se omite el smbolo "#" el manejador de tokens errneamente reconocer una cadena como E123 como un token valido del tipo EXPONENT (en lugar del IDENTIFIER en la gramtica de Java). -------------------------------------------------------------------------------complex_regular_expression_choices ::= complex_regular_expression ( "|" complex_regular_expression )* Las expresiones regulares complejas estn hechas de una liste de una o mas expresiones regulares complejas separadas por "|"s. Una coincidencia de una opcin de expresin regular compleja es la coincidencia de cualquiera de sus expresiones regulares complejas que la constituyen.

-------------------------------------------------------------------------------complex_regular_expression ::= ( complex_regular_expression_unit )*

Una expresin regular compleja es una secuencia de unidades de expresiones regulares complejas. Una coincidencia de una expresin regular compleja es una concatenacin de las coincidencias de las unidades de expresiones regulares. -------------------------------------------------------------------------------complex_regular_expression_unit ::= java_string_literal | "<" java_identifier ">" | character_list | "(" complex_regular_expression_choices ")" [ "+" | "*" | "?" ]

Una unidad de expresin regular compleja puede ser una literal de cadena de caracteres, en la cual existe solamente una coincidencia para esta unidad, denominada por la cadena de caracteres en si misma. Una unidad de expresin regular puede ser una referencia a otra expresin regular. La otra expresin regular tiene que ser etiquetada de tal manera que pueda ser referenciada. La coincidencia de sta unidad son todas las coincidencias de esta otra expresin regular. Tal referencia en expresiones regulares no puede inducir ciclos en la dependencia entre tokens. Una unidad de expresin regular compleja puede ser una lista de caracteres. Una lista de caracteres es la manera de definir un conjunto de caracteres. Una coincidencia de este tipo de expresiones regulares complejas es cualquier carcter permitido por la lista de caracteres. Una expresin regular compleja puede ser un conjunto de opciones como expresiones regulares entre parntesis. En este caso, una coincidencia valida de la unidad es cualquiera de las coincidencias anidadas. El conjunto de opciones entre parntesis puede opcionalmente seguir por: "+": Aqu cualquier coincidencia valida de la unidad es una o ms repeticiones de la coincidencia valida del conjunto de opciones entre parntesis. "*": Aqu cualquier coincidencia valida de la unidad es cero o ms repeticiones de una coincidencia valida del conjunto de opciones entre parntesis. "?": Aqu cualquier coincidencia valida de la unidad es tanto la cadena vaca como cualquier coincidencia valida de las opciones anidadas. Ntese que a pesar de las expansiones BNF, la expresin regular "[...]" no es equivalente a la expresin regular "(...)?". Esto es porque la construccin [...] es utilizada para describir la lista de caracteres en expresiones regulares. -------------------------------------------------------------------------------character_list ::= [ "~" ] "[" [ character_descriptor ( "," character_descriptor )* ] "]" Una lista de caracteres describe el conjunto de caracteres. Una coincidencia legal para una lista de caracteres es cualquier carcter en este conjunto. Una lista de caracteres es una lista de descriptores de caracteres separados por comas y dentro de parntesis

rectangulares. Cada descriptor de carcter describe un solo carcter o un rango de caracteres (ver la descripcin a continuacin) y esta es agregada al conjunto de caracteres de la lista de caracteres. Si la lista de caracteres comienza con el smbolo "~" el conjunto de caracteres es representado por cualquier carcter UNICODE no especificado en el conjunto especificado. -------------------------------------------------------------------------------character_descriptor::= java_string_literal ["-" java_string_literal]

Un descriptor de un carcter puede ser una cadena de solo caracter literal, en cuyo caso describe al mismo carcter; o si son dos caracteres separados por un guin -, en cuyo caso, describe el conjunto de todos los caracteres en el rango entre e incluyendo estos dos caracteres.

Potrebbero piacerti anche