Está en la página 1de 30

Instituto Tecnolgico

de la Costa Grande

QBASIC

PRESENTA

Garca Mayo Mara Elizabeth

MATERIA

LENGUAJES Y AUTOMATAS II

ZIHUATANEJO GUERRERO, MXICO


SEPTIEMBRE, 2013

NDICE DE CONTENIDO
NDICE DE CONTENIDO

ANTESCEDENTES

1.1

QBASIC

1.2

JavaCC

INTRODUCCION

CONTENIDO

3.1

Analisis lxico

3.2

Analisis sintctico

3.3

Analisis semntico

ANEXOS

4.1

Analizabasic.java

4.2

basicFrame.java

4.3

Tokenasignaciones.java

4.4

Lenguaje_QBASIC.jj

REFERENCIAS

1 ANTECEDENTES
1.1 QBASIC
QBasic fue creado con el objeto de reemplazar al BASIC y GW-BASIC alrededor de
1985 como un lenguaje de programacin para el usuario final.
Es un descendiente del lenguaje de programacin BASIC que Microsoft Corporation
desarroll para su uso con el sistema operativo MS-DOS.
Microsoft sac a la venta QuickBasic como un paquete de desarrollo comercial, lo
incluy como opcional en los discos de instalacin de Windows 95 y Windows 98,
incluido en el paquete olddos.exe, hasta Windows 2000 donde se dejo de distribuir pero
dejo la compatibilidad.
En su tiempo, QBasic provey de un IDE avanzado, incluyendo un depurador con
caractersticas tales como evaluacin de expresiones y modificacin del cdigo al vuelo.
Puede correr bajo casi todas las versiones del DOS y de Windows, o con
DOSBox/DOSEMU, en Linux y FreeBSD, su extensin es .BAS.
INSTRUCCIONES BSICAS
Las instrucciones bsicas incluyen palabras reservadas del lenguaje QBASIC. Lo que se
conoce comnmente como comandos. Independientemente de que los escribamos con
maysculas o minsculas, cuando QBASIC detecte que hemos escrito una palabra
asociada a un comando, automticamente lo escribir con letras maysculas.
REM
Sirve para introducir comentarios en el programa. Al ejecutar el programa, QBASIC no
tiene en cuenta las lneas que comienzan con el comando REM.
CLS
Borra la informacin que aparece en la pantalla. Conviene utilizar este comando al
comienzo del programa para eliminar la informacin de programas anteriores.
PRINT
Se utiliza para escribir datos en la pantalla. Con esta instruccin se pueden escribir
constantes o variables en pantalla, as como cadenas formadas por estas.
INPUT
Se utiliza para ingresar datos, y almacenarlos en una variable.

CONSTANTES Y VARIABLES
CONSTANTE:
Una constante es un dato cuyo valor no cambia durante la ejecucin del programa.
Puede ser:
Numrica: Una cifra, un valor numrico.
Alfanumrica: Cadena de caracteres encerrados entre comillas.
VARIABLE:
Una variable es una porcin de la memoria del ordenador que reservamos para
almacenar un valor. Para identificar esa zona de la memoria el cdigo del programa le
asigna un nombre. Al igual que las constantes las variables pueden ser numricas y
alfanumricas.
TIPOS DE DATOS
NOMBRE
STRING

SUFIJO

INTEGER
LONG

%
&

SINGLE

DOUBLE

DESCRIPCIN
Texto con
cualquier carcter
Nmeros enteros
Nmeros enteros
ms grandes
Nmeros con
decimales
Nmeros con ms
decimales

MNIMO Y MXIMO
0 a 32767
caracteres
-32768 a 32767
2.147.483.647 a
-2.147.483.648
2,8x1045 a -2,8x1045
4,9x10324 a
-4,9x10324

1.2 JavaCC
JavaCC es el principal metacompilador en JavaCC, tanto por sus posibilidades, como
por su mbito de difusin. Facilita la construccin de analizadores lxicos y sintcticos
por el mtodo de las funciones recursivas. De esta manera, los analizadores generados
utilizan la tcnica descendente a la hora de obtener el rbol sintctico.
Integra en una misma herramienta al analizador lexicogrfico y al sintctico, y el cdigo
que genera es independiente de cualquier biblioteca externa.
Algunas de sus caractersticas son:

Genera analizadores descendentes, permitiendo el uso de gramticas de


propsito general y la utilizacin de atributos durante la construccin del rbol
sintctico.
Las especificaciones lxicas y sintcticas se ubican en un solo archivo.
Admite el uso de estados lxicos y la capacidad de agregar acciones lxicas
incluyendo un bloque de cdigo Java tras el identificador de un token.
Incorpora distintos tipos de tokens.
Los tokens especiales son ignorados por el analizador generado, pero estn
disponibles para poder ser procesados por el desarrollador.
Forma parte del lenguaje Java
Es de cdigo abierto

Es altamente eficiente, lo que lo hace apto para entornos profesionales y lo ha


convertido en uno de los metacompiladores ms extendidos.

2 INTRODUCCION
A continuacin se mostraran los pasos para la realizacin de un compilador utilizando la
herramienta de Java, JavaCC.
El compilador fue hecho orientado al lenguaje de programacin QBASIC.
Y de acuerdo al anlisis lxico, sintctico y semntico que consisten en lo siguiente:

Lxico, se encarga de verificar que el usuario escriba bien palabras


Sintctico, se encarga de que los identificadores o palabras claves lleven el
orden adecuado
Semntico, se encarga de determinar el tipo de los resultados intermedios,
comprobar que los argumentos que tiene un operador pertenecen al conjunto de
los operadores posibles, y si son compatibles entre s, etc.

3 CONTENIDO
3.1 ANLISIS LXICO
Es la primera fase de un compilador consistente en un programa que recibe como
entrada el cdigo fuente de otro programa y produce una salida compuesta de tokens o
smbolos.
El anlisis lxico es el encargado de verificar que el usuario ha escrito bien las palabras
reservadas del lenguaje. Se define la declaracin de tokens en el archivo jj (javacc) para
que ah se almacenen las palabras reservadas del lenguaje que en este caso el lenguaje a
definir es QBASIC.
A continuacin un pequeo fragmento de cdigo donde se declaran tokens para las
palabras reservadas del lenguaje.
TOKEN: // Comillas
{
<Comillas : "\"">//12
| <Espacio : " ">//13
}
TOKEN :
{
<Pal_res_PRINT : ("PRINT" | "PRINT ")>//14
| <Pal_res_INPUT : ("INPUT" | "INPUT ")>//15
| <Pal_res_CLS : "CLS">//16
| <pal_res_REM : "REM">//17
| <pal_res_Com : "'">//18
| <pal_res_Pan : "SCREEN" | "SCREEN ">//19
| <pal_res_Col : "COLOR" | "COLOR ">//20
}

String lexico() :
{
String resultado;
}
{
( <Pal_res_PRINT> { resultado = new String(token.image); tipo = new
String("Etiqueta PRINT");}
.
.
.
.

}
Anexos: Lenguaje_QBASIC.jj

3.2 ANLISIS SINTCTICO


El anlisis sintctico convierte el texto de entrada en otras estructuras, que son ms
tiles para el posterior anlisis y capturan la jerarqua implcita de la entrada. Un
analizador lxico crea tokens de una secuencia de caracteres de entrada y son estos
tokens los que son procesados por el analizador sintctico para construir la estructura de
datos.
Es el encargado de verificar que el orden de los identificadores sea el adecuado. Esto se
refiere a que el cdigo siga la estructura correcta. Que en este caso podra ser -> PRINT
HOLA, esto est escrito de la manera correcta.
A continuacin un pequeo fragmento de cdigo referente al analizador sintactico:
void codigo() :
{}
{
(cuerpo())*
}
void cuerpo() :
{}
{
limpiar()
| Mensaje()
| IngresaDato()
| Comentarios()
| Expresiones()
| Apariencia()
}
void Mensaje() :
{}
{
<Pal_res_PRINT> ( <Cadena> | <Identifier>(<EOL>|<single>| <LONG>| <DOUBLE>)?
(( <Resta>|<Multi> | <Divide>| <Mod> |
<Potencia>)<Identifier>)?)
(
(<MAS>|
<DELIMITADOR>)(<Espacio>)?<Identifier>(<EOL>|<Mod>|<single>|
<LONG>|
<DOUBLE> )? )?
}
Anexos: Lenguaje_QBASIC.jj

3.3 ANALISIS SEMANTICO


Es el encargado de verificar que se realicen asignaciones correctas donde se utiliza una
tabla de smbolos, que en este caso se utiliz una tabla tipo hash en la cual se inserta el
tipo y el nombre de la variable, y despus se verifica si se asign de la forma correcta,
as como las asignaciones de operaciones aritmticas con estas. La tabla de smbolos se
manda a llamar desde el archivo JavaCC y est declarada en un archivo java.
A continuacin un pequeo fragmento de cdigo.
Aqu se manda a llamar desde el archivo jj (JavaCC) y se envan los parmetros de la
expresin para identificar que estn bien escritos y las asignaciones sean correctas:
void lenguaje() :
{
TokenAsignaciones.SetTables();
}
{
codigo() <EOF>
}
//Sentencia ASIGNACION
void Expresiones():
{
Token v1;
Token v2;
Token v3;
int aux;
String res;
boolean imp = false;
}
{
v1 = <Identifier>
(<Asignacion>
(TiposAsignaciones())
{
v2 = token;
.
.
.
.
}
Anexos: Lenguaje_QBASIC.jj

Recibe los token y los compara dentro de la tabla hash:


public static void InsertarSimbolo(Token identificador, int tipo){
tabla.put(identificador.image, tipo);
}

public static void SetTables(){


/*En este metodo se inicializan las tablas, las cuales almacenaran los tipo
e datos compatibles con:
entero = intComp
decimal = decComp
cadena = strComp
caracter = chrComp
*/
intComp.add(23);
decComp.add(25);
strComp.add(26);
}
Anexos: TokenAsignaciones.java

4 ANEXOS
Para mejor comprensin del compilador a continuacin se mostraran los cuatro archivos
utilizados para la realizacin del mismo, los cuales consisten en tres archivos .java y
un archivo .jj
4.1 Analizabasic.java
Programa principal del cual se mandan a llamar todos los dems archivos.
public class Analizabasic {
public static void main(String[] args){
basicFrame frame = new basicFrame();
frame.setVisible(true);
}
}
4.2 basicFrame.java
Contiene el cdigo orientado a objetos del compilador, hace uso de las funciones del
archivo JavaCC.
/*
Descripcion: Archivo en el que se crea el frame y los elementos principales del mismo,
como el menu, que permite mandar llamar el procedimiento que compila el codigo
antes escrito.
*/
import java.awt.*;

import java.awt.event.*;
import javax.swing.*;
import java.io.*;
import javax.swing.filechooser.FileNameExtensionFilter;
import java.util.*;
import javax.swing.text.*;
import java.util.HashMap;
import java.awt.datatransfer.StringSelection;
import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.*;
public class basicFrame extends JFrame{
//Se crean los componentes a utilizar
public JTextPane txtCodigo = new JTextPane();
public JTextPane txtTokens = new JTextPane();
public JTextArea txtError = new JTextArea();
private JScrollPane jScrollPane1 = null;
private JScrollPane jScrollPane2 = null;
private JScrollPane jScrollPane3 = null;
private JPanel pnlCentral = new JPanel();
private BorderLayout layoutMain = new BorderLayout();
private BorderLayout borderLayout1 = new BorderLayout();
//Estos permiten aadir estilos al texto escrito
private StyledDocument EstiloDocumento = null, EstiloDocumento2 = null;
private MutableAttributeSet AtributosError = null, AtributosNormal = null;
//Variables globales
private File file;
private FileInputStream fin;
Boolean salir;
int contador = 0;
StringTokenizer Arreglo_de_tokens;
//Constructor
public basicFrame(){
//Se establece el estilo a usar c uando ocurre error
txtCodigo.setFont(new Font("Courier New", 0, 14));
EstiloDocumento = txtCodigo.getStyledDocument();
AtributosError = new SimpleAttributeSet();
StyleConstants.setBackground(AtributosError, Color.YELLOW);
txtError.setFont(new Font("Courier New", 0, 14));
txtError.setBackground(new Color(235, 235, 235));
//Se establece el estilo a usar cuando se esta corrigiendo un error
EstiloDocumento2 = txtCodigo.getStyledDocument();
AtributosNormal = new SimpleAttributeSet();
StyleConstants.setBackground(AtributosNormal, Color.WHITE);
//Componente a utilizar

JMenuBar menuBar = new JMenuBar();


JMenu menuArchivo = new JMenu();
JMenuItem menuArchivoSalir = new JMenuItem();
JMenuItem menuArchivoAbrir = new JMenuItem();
JMenuItem menuArchivoGuardar = new JMenuItem();
JMenuItem menuArchivoGuardarC = new JMenuItem();
menuArchivo.setText("Archivo");
menuArchivoAbrir.setText("Abrir");
menuArchivoGuardar.setText("Guardar");
menuArchivoGuardarC.setText("Guardar como...");
menuArchivoSalir.setText("Salir");
JMenu menuEditar = new JMenu();
menuEditar.setText("Editar");
JMenuItem menuCopiar = new JMenuItem();
JMenuItem menuCortar = new JMenuItem();
JMenuItem menuPegar = new JMenuItem();
menuCopiar.setText("Copiar");
menuCortar.setText("Cortar");
menuPegar.setText("Pegar");
JMenu menuAnalizar = new JMenu();
JMenuItem menuAnalizarCompilar = new JMenuItem();
menuAnalizar.setText("Analisis");
menuAnalizarCompilar.setText("Compilar");
JMenu menuAyuda = new JMenu();
menuAyuda.setText("Ayuda...");
JMenuItem menuAcercaDe = new JMenuItem();
menuAcercaDe.setText("Acerda de...");
menuArchivoAbrir.addActionListener(
new ActionListener(){
public void actionPerformed(ActionEvent e){
basicFrame.this.Abrir();
}
}
);
menuArchivoGuardar.addActionListener(
new ActionListener(){
public void actionPerformed(ActionEvent e){
basicFrame.this.Guardar();
}
}
);
menuArchivoGuardarC.addActionListener(
new ActionListener(){

public void actionPerformed(ActionEvent e){


basicFrame.this.GuardarC();
}
}
);
//Se aade el Actionlistener para la opcion Salir
menuArchivoSalir.addActionListener(
new ActionListener(){
public void actionPerformed(ActionEvent e){
basicFrame.this.Salir();
}
}
);
menuCopiar.addActionListener(
new ActionListener(){
public void actionPerformed(ActionEvent e){
basicFrame.this.Copiar(txtCodigo.getSelectedText());
}
}
);
menuCortar.addActionListener(
new ActionListener(){
public void actionPerformed(ActionEvent e){
basicFrame.this.Cortar(txtCodigo.getSelectedText());
}
}
);
//Se aade el Actionlistener para la opcion Salir
menuPegar.addActionListener(
new ActionListener(){
public void actionPerformed(ActionEvent e){
basicFrame.this.Pegar();
}
}
);
//se aade el actionlistener para la opcion analisis lexico
menuAnalizarCompilar.addActionListener(
new ActionListener(){
public void actionPerformed(ActionEvent e){
basicFrame.this.AnalisisCompilar();
}
}
);
//Se aade el actionlistener para la opcion acerca de

menuAcercaDe.addActionListener(
new ActionListener(){
public void actionPerformed(ActionEvent e){
basicFrame.this.AcercaDe();
}
}
);
/*se aade un key listener para recuperar el estilo normal de txtCodigo*/
txtCodigo.addKeyListener(new KeyAdapter(){
public void keyTyped(KeyEvent e){
char caracter = e.getKeyChar();
RecuperaEstilo();
}
});
//se aaden las opciones disponibles al menu
menuArchivo.add(menuArchivoAbrir);
menuArchivo.add(menuArchivoGuardar);
menuArchivo.add(menuArchivoGuardarC);
menuArchivo.add(menuArchivoSalir);
menuEditar.add(menuCopiar);
menuEditar.add(menuCortar);
menuEditar.add(menuPegar);
menuAnalizar.add(menuAnalizarCompilar);
menuAyuda.add(menuAcercaDe);
menuBar.add(menuArchivo);
menuBar.add(menuEditar);
menuBar.add(menuAnalizar);
menuBar.add(menuAyuda);
//proporccionar un medio para acomodar los componentes
this.getContentPane().setLayout(layoutMain);
pnlCentral.setLayout(borderLayout1);
//se crea instancias y se aaden componentes al panel principal
jScrollPane1 = new JScrollPane(txtCodigo,JScrollPane.VERTICAL_SCROLLBA
R_ALWAYS,JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);
jScrollPane2 = new JScrollPane(txtTokens,JScrollPane.VERTICAL_SCROLLBA
R_ALWAYS, JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);
jScrollPane3 = new JScrollPane(txtError,JScrollPane.VERTICAL_SCROLLBA
R_ALWAYS, JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);
pnlCentral.add(jScrollPane1, BorderLayout.CENTER);
//SE aaden componentes al frame
this.getContentPane().add(pnlCentral, BorderLayout.CENTER);
this.getContentPane().add(jScrollPane2, BorderLayout.EAST);
this.getContentPane().add(jScrollPane3, BorderLayout.SOUTH);
setTitle("QBASIC");
setJMenuBar(menuBar);

setSize(new Dimension(600, 400));


setLocationRelativeTo(null);
// Se aade un Windows Listener para cuando se cierre el frame
this.addWindowListener(
new WindowAdapter(){
public void windowClosing(WindowEvent e){
basicFrame.this.Salir();
}
}
);
}
/* Procedimiento que cambia las propiedades del componente txtCodigo si ocurre
un error */
public void coloreaTexto(int inicio, int longitud) {
EstiloDocumento.setCharacterAttributes(inicio-1, longitud, AtributosError,true)
}

/* Procedimiento que regresa las propiedades del componente txtCodigo si se


escribe algo en el componente txtCodigo */
public void RecuperaEstilo() {
EstiloDocumento2.setCharacterAttributes(0, txtCodigo.getText().length(),
.
AtributosNormal, true);
}
// Lo que sucede al pulsar el boton
public void Abrir() {
JFileChooser fileChooser = new JFileChooser(".");
fileChooser.setFileFilter(new FileNameExtensionFilter("Todos los archivos
*.bas", "bas","BAS"));
fileChooser.setDialogTitle("Abrir Archivo");
int returnValue = fileChooser.showOpenDialog(null);
if (returnValue == JFileChooser.APPROVE_OPTION) {
File selectedFile = fileChooser.getSelectedFile();
/*System.out.println(selectedFile.getParent());
System.out.println(selectedFile.getName());
txtCodigo.setText(String.valueOf(selectedFile));*/
try{
String nombre = selectedFile.getName();
String path = selectedFile.getAbsolutePath();
String contenido = getArchivo( path );
//Colocamos en el titulo de la aplicacion el
//nombre del archivo
this.setTitle( nombre );
//En el editor de texto colocamos su contenido

txtCodigo.setText( contenido );
}catch( Exception exp){}
}
}
public String getArchivo( String ruta ){
FileReader fr = null;
BufferedReader br = null;
//Cadena de texto donde se guardara el contenido del archivo
String contenido = "";
try{
//ruta puede ser de tipo String o tipo File
fr = new FileReader( ruta );
br = new BufferedReader( fr );
String linea;
//Obtenemos el contenido del archivo linea por linea
while( ( linea = br.readLine() ) != null ){
contenido += linea + "\n";
}
}catch( Exception e ){ }
finally
{
try{
br.close();
}catch( Exception ex ){}
}
return contenido;
}
public void Guardar(){

JFileChooser fileChooser = new JFileChooser(".");


fileChooser.setFileFilter (new FileNameExtensionFilter("Todos los archivos
*.bas", "bas","BAS"));
fileChooser.setDialogTitle("Guardar Archivo");
int returnValue = fileChooser.showSaveDialog(null);
if (returnValue == JFileChooser.APPROVE_OPTION) {
File selectedFile = fileChooser.getSelectedFile();
System.out.println(selectedFile.getParent());
System.out.println(selectedFile.getName());
FileWriter fw;
try
{
fw= new FileWriter(selectedFile.getName());
}

catch(IOException io)
{
txtCodigo.setText("Error al abrir el fichero");
return;
}
//Escribimos
try
{
fw.write(txtCodigo.getText());
txtTokens.setText("Fichero guardado");
}
catch(IOException io)
{
txtError.setText("Error al escribir");
}
//cerramos el fichero
try
{
fw.close();
}
catch(IOException io)
{
txtError.setText("Error al cerrar el archivo");
}
}
}

..

public void GuardarC() {


JFileChooser fileChooser = new JFileChooser(".");
fileChooser.setFileFilter(new FileNameExtensionFilter("Todos los
archivos *.bas", "bas","BAS"));
fileChooser.setDialogTitle("Guardar Archivo");
int returnValue = fileChooser.showSaveDialog(null);
if (returnValue == JFileChooser.APPROVE_OPTION) {
File selectedFile = fileChooser.getSelectedFile();
System.out.println(selectedFile.getParent());
System.out.println(selectedFile.getName());
FileWriter fw;
try
{
fw= new FileWriter(selectedFile.getName());
}
catch(IOException io)
{

. ...

txtCodigo.setText("Error al abrir el fichero");


return;
}
//Escribimos
try
{
fw.write(txtCodigo.getText());
txtTokens.setText("Fichero guardado");
}
catch(IOException io)
{
txtError.setText("Error al escribir");
}
//cerramos el fichero
try
{
fw.close();
}
catch(IOException io)
{
txtError.setText("Error al cerrar el archivo");
}
}
}
public void Copiar(String copiar){
Clipboard cb = Toolkit.getDefaultToolkit().getSystemClipboard();
if (copiar == null)
return;
StringSelection as = new StringSelection(copiar);
cb.setContents(as, as);
}
public void Cortar(String cortar){
Clipboard cb = Toolkit.getDefaultToolkit().getSystemClipboard();
if (cortar == null)
return;
StringSelection clipString = new StringSelection(cortar);
cb.setContents(clipString, clipString);
txtCodigo.replaceSelection("");
}
public void Pegar(){
Clipboard cb = Toolkit.getDefaultToolkit().getSystemClipboard();
Transferable clipData = cb.getContents(null);
if(clipData.isDataFlavorSupported(DataFlavor.stringFlavor)){

try {
String
resultado
(String)clipData.getTransferData(DataFlavor.stringFlavor);
String txt = txtCodigo.getText();
txtCodigo.setText(txt+resultado);
} catch (Exception ex) {
System.err.println("Not String flavor");

}
}
}
// Procedimiento para cerrar la aplicacin
protected void Salir() {
// Salir de la aplicacin
System.exit(0);
}
/* Procedimiento que encarga de mandar llamar los analizadores lxico y
* sintctico */
protected void AnalisisCompilar() {
// Se crean declaran lo respectivo a los archivos a utilizar
FileInputStream archivo_temp, archivo_temp2;
FileOutputStream fout;
PrintWriter pw;
// Se declaran las variables a utilziar
String archivo = Long.toString(System.currentTimeMillis()) + ".txt";
String respTokens = "";
String []respTokens2 = txtCodigo.getText().split("\n");
salir = false;
try {
fout = new FileOutputStream(archivo);
pw = new PrintWriter(fout);
pw.print(txtCodigo.getText());
pw.close();
fout.close();
} catch (IOException ioe) {
txtError.setText("Error de escritura en el archivo");
}
/* Procedimiento que manda llamar a los analizadores lxico y
* sintctico */
try {
BASIC comp;
archivo_temp = new FileInputStream(archivo);
comp = new BASIC(archivo_temp);
comp.setEditor(this);
Arreglo_de_tokens
=
new
StringTokenizer(txtCodigo.getText());

String
tokens[]
String[Arreglo_de_tokens.countTokens()];
txtTokens.setText("");
txtError.setText("");

new

try {
comp.lenguaje();
} catch(ParseException pe){
comp.addError("Error en el proceso de Compilacion - " +
pe.toString(), comp.token);
salir = true;
} catch(Error e){
comp.addError("Error en el proceso de Compilacion - " +
e.toString(), comp.token);
salir = true;
}
archivo_temp.close();
if (salir == false){
archivo_temp2 = new FileInputStream(archivo);
// Se manda dicho archivo al constructor en HTML
comp = new BASIC(archivo_temp2);
// Se establece el editor por defecto
comp.setEditor(this);
// Se prueba escribir los tokens en el componente txtTokens
try{
do{// ciclo do while modificar , agregar un gaurda como
if(respTokens == "")
respTokens = comp.lexico() + " - " + comp.tipo;
else
respTokens = respTokens + "\n" + comp.lexico()
+ " - " + comp.tipo;
.
}
while(comp.resultado1=="1");//System.out.println(comp.lexic
o());
txtTokens.setText(respTokens);
} catch(ParseException pe){
comp.addError("Error en el proceso de Compilacion - " +
pe.toString(), comp.token);
}
archivo_temp2.close();
}
File file = new File(archivo);
if(!file.delete())
comp.addError("No se pudo borrar archivo = " + archivo, null);
comp = null;
this.resize(750, 600);
txtTokens.resize(300, 650);
this.repaint();

txtError.resize(650, 200);
this.repaint();
this.resize(600, 400);
this.repaint();
}catch (IOException ioe){
txtError.setText("Error de apertura del archivo.");
}
}
//procedimiento acerca de..
protected void AcercaDe(){
System.out.println("Acerca de...");
JOptionPane.showMessageDialog(null, "Unidad 1 - practica . \n" + "Materia:
Lenguajes y Automatas II. \n");
}
}
4.3 Tokenasignaciones.java
En este archivo se hace la creacin de las tablas hash para llevar a cabo el anlisis
semntico.
import java.io.PrintStream;
import java.util.Hashtable;
import java.lang.String;
import java.util.ArrayList;
class TokenAsignaciones
{
//Variable para validar asignaciones a caracteres(ichr)
public static int segunda = 0;
//Tabla que almacenara los tokens declarados
private static Hashtable tabla = new Hashtable();
//Listas que guardaran los tipos compatibles de las variables
private static ArrayList<Integer> intComp = new ArrayList();
private static ArrayList<Integer> decComp = new ArrayList();
private static ArrayList<Integer> strComp = new ArrayList();
//variable
//tipoDato
public static void InsertarSimbolo(Token identificador, int tipo)
{
//En este metodo se agrega a la tabla de tokens el identificador que esta siendo
declarado junto con su tipo de dato
tabla.put(identificador.image, tipo);
}
public static void SetTables(){
intComp.add(23);

decComp.add(25);
strComp.add(26);
}
public static String checkAsing(Token TokenIzq, Token TokenAsig)
{
//variables en las cuales se almacenara el tipo de dato del identificador y de las
asignaciones (ejemplo: n1(tipoIdent1) = 2(tipoIdent2) + 3(tipoIdent2))
int tipoIdent1;
int tipoIdent2;
/* De la tabla obtenemos el tipo de dato del identificador asi como, si el token
enviado es diferente a algun tipo que no se declara como los numeros(48), los
decimales(50), caracteres(52) y cadenas(51) entonces tipoIdent1 = tipo_de_dato, ya
que TokenAsig es un dato*/
if(TokenIzq.kind != 23 && TokenIzq.kind != 25)
{
try
{
tipoIdent1 = (Integer)tabla.get(TokenIzq.image);
}
catch(Exception e)
{
//Si TokenIzq.image no se encuentra en la tabla en la cual se agregan los
.....
//tokens, el token no ha sido declarado, y se manda un error
return "Error: El identificador " + TokenIzq.image + " No ha sido declarado
\r\nLinea: " + TokenIzq.beginLine;
}
}
else
tipoIdent1 = 0;
if(TokenAsig.kind == 24)
{
/*Si el tipo de dato que se esta asignando, es algun identificador(kind == 49)
se obtiene su tipo de la tabla de tokens para poder hacer las comparaciones*/
try
{
tipoIdent2 = (Integer)tabla.get(TokenAsig.image);
}
catch(Exception e)
{
//si el identificador no existe manda el error
return "Error: El identificador " + TokenAsig.image + " No ha sido
declarado \r\nLinea: " + TokenIzq.beginLine;
}
}
//Si el dato es entero(48) o decimal(50) o caracter(51) o cadena(52)
//tipoIdent2 = tipo_del_dato
else if(TokenAsig.kind == 23 || TokenAsig.kind == 25 || TokenAsig.kind == 26)
tipoIdent2 = TokenAsig.kind;

else
tipoIdent2 = 0;
if(tipoIdent1 == 23) //Int
{
//Si la lista de enteros(intComp) contiene el valor de tipoIdent2, entonces es .
//compatible y se puede hacer la asignacion
if(intComp.contains(tipoIdent2))
return " ";
else //Si el tipo de dato no es compatible manda el error
return "Error: No se puede convertir " + TokenAsig.image + " a Entero
\r\nLinea: " + TokenIzq.beginLine;
}
else if(tipoIdent1 == 25) //double
{
if(decComp.contains(tipoIdent2))
return " ";
else
return "Error: No se puede convertir " + TokenAsig.image + " a Decimal
\r\nLinea: " + TokenIzq.beginLine;
} else if(tipoIdent1 == 26) //string
{
if(strComp.contains(tipoIdent2))
return " ";
else
return "Error: No se puede convertir " + TokenAsig.image + " a Cadena
\r\nLinea: " + TokenIzq.beginLine;
}
else
{
return "El Identificador " + TokenIzq.image + " no ha sido declarado" + "
Linea: " + TokenIzq.beginLine;
}

}
/*Metodo que verifica si un identificador ha sido declarado,
ej cuando se declaran las asignaciones: i++, i--)*/
public static String checkVariable(Token checkTok){
try
{
//Intenta obtener el token a verificar(checkTok) de la tabla de los tokens
int tipoIdent1 = (Integer)tabla.get(checkTok.image);
return " ";
}
catch(Exception e)
{
//Si no lo puede obtener, manda el error
return "Error: El identificador " + checkTok.image + " No ha sido declarado
\r\nLinea: " + checkTok.beginLine;

}
}
}
4.4 Lenguaje_QBASIC.jj
Archivo de JavaCC donde se crean los tokens para el anlisis del compilador:
options {
LOOKAHEAD = 1;
CHOICE_AMBIGUITY_CHECK = 2;
OTHER_AMBIGUITY_CHECK = 1;
STATIC = false; //Esta opcion es importante para integrar el analizador al editor
DEBUG_PARSER = false;
DEBUG_LOOKAHEAD = false;
DEBUG_TOKEN_MANAGER = false;
ERROR_REPORTING = true;
JAVA_UNICODE_ESCAPE = false;
UNICODE_INPUT = false;
IGNORE_CASE = true; // Esta opcion ignora la diferencia entre mayusculas y
//minusculas
USER_TOKEN_MANAGER = false;
USER_CHAR_STREAM = false;
BUILD_PARSER = true;
BUILD_TOKEN_MANAGER = true;
SANITY_CHECK = true;
FORCE_LA_CHECK = false;
}
PARSER_BEGIN(BASIC)
//AQUI SE PUEDEN IMPORTAR LOS PAQUETES QUE SEAN NECESARIOS
import java.io.FileInputStream;
import java.io.IOException;
import javax.swing.JEditorPane;
import javax.swing.JScrollPane;
import java.awt.Color;
public class BASIC {
public basicFrame editor = null; //Variable para referenciar al editor
public String tipo = "";
public String errores = "";
public void setEditor(basicFrame ed){
editor = ed;
}

public void addError(String err, Token t){


if(editor != null){
errores = errores + err + "\n";
editor.txtError.setText(errores);
if(t != null){
editor.coloreaTexto(t.beginColumn, t.toString().length());
}else{
System.out.println(err);
}
}
}
}
PARSER_END(BASIC)
SKIP:
{
"\r" | "\t" | "\n"
}
TOKEN : /* Operadores */
{
< Asignacion : "=" | " = " | "= " | " ="> // Kind 4
| <MAS : "+" | "+ " | " + " | " +" > // Kind 5
| <Resta:"-" | "- " | " - " | " -"> // Kind 6
| <Multi:"*" | "* " | " * " | " *"> // Kind 7
| <Divide:"/" | "/ " | " / " | " /"> // Kind 8
| <Mod:"%" | "% " | " % " | " %">//9//INTEGER
| <Potencia:"^" | "^ " | " ^ " | " ^">//10
}
TOKEN:
{
<EOL : "$">//11 STRING
//<
}
TOKEN: // Comillas
{
<Comillas : "\"">//12
| <Espacio : " ">//13
}
TOKEN :
{
<Pal_res_PRINT : ("PRINT" | "PRINT ")>//14
| <Pal_res_INPUT : ("INPUT" | "INPUT ")>//15
| <Pal_res_CLS : "CLS">//16
| <pal_res_REM : "REM">//17
| <pal_res_Com : "'">//18
| <pal_res_Pan : "SCREEN" | "SCREEN ">//19

| <pal_res_Col : "COLOR" | "COLOR ">//20


}
TOKEN: // DELIMITADOR
{
<DELIMITADOR: (<DEL> )+ >//21
| <#DEL : [";"]>//22
}
TOKEN:
{
<Number : (["0"-"9"])+> // Kind 23
| <Identifier : ["a"-"z","A"-"Z"](["a"-"z","A"-"Z","0"-"9","_"])*> // Kind 24
| <Decimal : (<Espacio>)*(["0"-"9"])+["."](["0"-"9"])+ > // Kind 25
| <Cadena : (<Espacio>)*<Comillas>["a"-"z","A"-"Z","0"-"9"," ","?"]
(["a"-"z","A"-"Z","0"-"9"," ",":",";",".","?"])*<Comillas>> // Kind 26
| <DoublePoint : ":"> // Kind 27
| <Coma : ","> //kind 28
}
TOKEN: // Contenido / digito / letra
{
<CONTENIDO: (<Comillas> (<digito> | <letra> | <simbolo> | <Espacio> |
<MAS>)+ <Comillas>) >
| <#digito : ["0" - "9"]>
| <#letra : ["A" - "Z", "a" - "z"]>
| <#simbolo : [":", "@", "-", ".", "_", "%", "*"]>
}
//tipos de datos
TOKEN:
{
< single: "!">//dECIMAL
|< LONG: "&">//ENTERO LARGO
|< DOUBLE: "#">//dECIMAL LARGO
}
String lexico() :
{
String resultado;
}
{
( <Pal_res_PRINT> { resultado = new String(token.image);
String("Etiqueta PRINT");}
| <Pal_res_INPUT> { resultado = new String(token.image);
String("Etiqueta INPUT");}
| <Pal_res_CLS> { resultado = new String(token.image);
String("Etiqueta CLS");}
| <pal_res_REM> { resultado = new String(token.image);
String("Etiqueta COMENTARIOS");}

tipo = new
tipo = new
tipo = new
tipo = new

| <pal_res_Com> { resultado = new String(token.image); tipo = new


String("Etiqueta COMENTARIOS");}
| <pal_res_Pan> { resultado = new String(token.image); tipo = new
String("Etiqueta PANTALLA");}
| <pal_res_Col> { resultado = new String(token.image); tipo = new
String("Etiqueta COLOR");}
| <Comillas> { resultado = new String(token.image); tipo = new String("Etiqueta
COMILLAS");}
| <DELIMITADOR> { resultado = new String(token.image); tipo = new
String("Etiqueta DELIMITADOR");}
| <CONTENIDO> { resultado = new String(token.image); tipo = new
String("Etiqueta CONTENIDO");}
| <Espacio> { resultado = new String(token.image); tipo = new String("Etiqueta
Espacio");}
| <Coma> { resultado = new String(token.image); tipo = new String("Etiqueta
COMA");}
| <single> { resultado = new String(token.image); tipo = new String("Single");}
| <LONG> { resultado = new String(token.image); tipo = new String("Etiqueta
LONG");}
| <DOUBLE> { resultado = new String(token.image); tipo = new
String("Etiqueta DOUBLE");}
| <Number> { resultado = new String(token.image);
String("NUMERO");}
| <Identifier> { resultado = new String(token.image);
String("IDENTIFICADOR");}
| <Decimal> { resultado = new String(token.image);
String("DECIMAL");}
| <Cadena> { resultado = new String(token.image);
String("CADENA");}
| <DoublePoint> { resultado = new String(token.image);
String("DOS PUNTOS");}

tipo

new

tipo = new
tipo

new

tipo

new

tipo = new

| <MAS> { resultado = new String(token.image); tipo = new String("SUMA");}


| <Asignacion> { resultado = new String(token.image); tipo = new
String("ASIGNACION");}
| <Resta> { resultado = new String(token.image); tipo = new String("RESTA");}
| <Multi> { resultado = new String(token.image); tipo = new
String("MULTIPLICACION");}
| <Divide> { resultado = new String(token.image); tipo = new
String("DIVIDE");}
| <Mod> { resultado = new String(token.image); tipo = new String("Div
modular");}
| <Potencia> { resultado = new String(token.image); tipo = new
String("POTENCIA");}

| <EOL> { resultado = new String(token.image); tipo = new String("FIN


VARIABL");}
| <EOF> { resultado = new String(token.image); tipo = new String("FIN DE
ARCHIVO");}
)
{
return resultado;
}
}
void lenguaje() :
{
TokenAsignaciones.SetTables();
}
{
codigo() <EOF>
}
void codigo() :
{}
{
(cuerpo())*
}
void cuerpo() :
{}
{
limpiar()
| Mensaje()
| IngresaDato()
| Comentarios()
| Expresiones()
| Apariencia()
}
//Sentencia ASIGNACION
void Expresiones():
{
Token v1;
Token v2;
Token v3;
int aux;
String res;
boolean imp = false;
}
{
v1 = <Identifier>
(<Asignacion>
(TiposAsignaciones())
{

v2 = token;
TokenAsignaciones.InsertarSimbolo(v1, v2.kind);
TokenAsignaciones.InsertarSimbolo(v2, v2.kind);
res = TokenAsignaciones.checkAsing(v1, v2);
if(res != " ")
{
System.out.println(res);
imp = true;
}
}
(LOOKAHEAD(2)OpAritmetico()
TiposAsignaciones()
{
v3 = token;
TokenAsignaciones.InsertarSimbolo(v3, v3.kind);
res = TokenAsignaciones.checkAsing(v1, v3);
if(res != " " && !imp)
{
System.out.println(res);
}
})*
)
}
void TiposAsignaciones() :
{}
{
<Number>
| <Identifier>
| <Cadena>
| <Decimal>
}
void OpAritmetico() :
{}
{
<MAS>
| <Resta>
| <Multi>
| <Divide>
| <Mod>
| <Potencia>
}
void limpiar() :
{}
{

<Pal_res_CLS>
}
void Mensaje() :
{}
{
<Pal_res_PRINT> ( <Cadena> | <Identifier>(<EOL>|<single>| <LONG>|
<DOUBLE>)?(( <Resta>|<Multi> | <Divide>| <Mod>
| <Potencia>)<Identifier>)?)
(
(<MAS>|<DELIMITADOR>)(<Espacio>)?<Identifier>(<EOL>|<Mod>|<single>|
<LONG>| <DOUBLE> )? )?
}
void IngresaDato() :
{}
{
<Pal_res_INPUT>(<Cadena>(<Coma>|<DELIMITADOR>))?(<Espacio>)?
<Identifier>(<EOL>|<Mod>|<single>| <LONG>| <DOUBLE> )?
}
void Comentarios() :
{}
{
(<pal_res_REM><Cadena>)
|(<pal_res_Com><Cadena>)
}
void Apariencia() :
{}
{
(<pal_res_Col><Number><Coma><Number>)
|(<pal_res_Pan><Number>)
}

5 REFERENCIAS
Java a Tope: Compiladores - Traductores y Compiladores con Lex/Yacc, JFlex/Cup y
JavaCC.
Autores: Sergio Galvez Rojas, Miguel Angel Mora Mata
Editorial :Universidad de Malaga
[1995-1997] etsimo WWW team
http://www6.uniovi.es/qbasic/qbasic1.html
Garca Merayo, Flix; Alcalde Lancharro, Eduardo (4 de 1998) (en Espaol).
Programacin bsica con Logo y QBasic : (gua prctica para estudiantes) (1 edicin).
McGraw-Hill / Interamericana de Espaa, S.A.. pp. 64.
Moldes Teo, Francisco Javier (9 de 1991) (en Espaol). QBasic (1 edicin). Anaya
Multimedia-Anaya Interactiva. pp. 272.