Initial Commit
This commit is contained in:
Executable
+271
@@ -0,0 +1,271 @@
|
||||
/* basic application to be extended
|
||||
*/
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.*;
|
||||
import java.util.ArrayList;
|
||||
|
||||
public class Basic extends JFrame implements Runnable, KeyListener,
|
||||
MouseListener,
|
||||
MouseMotionListener,
|
||||
WindowListener
|
||||
{
|
||||
protected static int FPS = 50; // desired frames per second
|
||||
|
||||
private int stepNumber;
|
||||
|
||||
// part of the basic framework
|
||||
private Thread theThread; //to control the animation
|
||||
|
||||
private boolean waiting;
|
||||
|
||||
protected int pixelWidth, pixelHeight; // dimensions of window in pixels
|
||||
private int ulcX, ulcY; // location of upper left corner of window on screen
|
||||
|
||||
private Color backgroundColor; // background color of entire window
|
||||
|
||||
private double mouseX, mouseY; // maintain correct mouse location
|
||||
private int whichCamera; // maintain which camera's pixel grid region mouse is in
|
||||
|
||||
private Graphics dbg;
|
||||
private Image dbImage = null;
|
||||
|
||||
protected ArrayList<Camera> cameras;
|
||||
|
||||
public Basic( String title, int ulx, int uly, int pw, int ph )
|
||||
{
|
||||
super( title ); // call JFrame
|
||||
|
||||
ulcX = ulx; ulcY = uly;
|
||||
pixelWidth = pw; pixelHeight = ph;
|
||||
|
||||
setBounds(ulcX, ulcY, pixelWidth, pixelHeight );
|
||||
setResizable( false );
|
||||
|
||||
addKeyListener(this);
|
||||
// setFocusable(true);
|
||||
// requestFocus();
|
||||
addMouseListener(this);
|
||||
addMouseMotionListener(this);
|
||||
addWindowListener(this);
|
||||
|
||||
cameras = new ArrayList<Camera>();
|
||||
|
||||
stepNumber = 0;
|
||||
|
||||
// force mouse to be in center of window at start
|
||||
mouseX = pixelWidth/2;
|
||||
mouseY = pixelHeight/2;
|
||||
|
||||
}
|
||||
|
||||
public void start()
|
||||
{
|
||||
setVisible(true);
|
||||
|
||||
// physically draw the mouse cursor where we want it
|
||||
try{
|
||||
Robot rob = new Robot();
|
||||
rob.mouseMove( ulcX+pixelWidth/2, ulcY+pixelHeight/2 );
|
||||
}catch(Exception e){}
|
||||
|
||||
if (theThread == null)
|
||||
theThread = new Thread(this);
|
||||
theThread.start();
|
||||
}
|
||||
|
||||
public void run()
|
||||
{
|
||||
while (true)
|
||||
{
|
||||
stepNumber++;
|
||||
|
||||
long startTime = System.nanoTime();
|
||||
|
||||
render();
|
||||
paintScreen();
|
||||
|
||||
long stopTime = System.nanoTime();
|
||||
|
||||
double elapsed = (stopTime-startTime)/1000000.0; // milliseconds
|
||||
|
||||
int waitTime = 1000/FPS - (int) Math.round( elapsed );
|
||||
if( waitTime < 1 )
|
||||
waitTime = 1;
|
||||
|
||||
try {
|
||||
Thread.sleep(waitTime);
|
||||
}
|
||||
catch (InterruptedException ie)
|
||||
{System.err.println("OOPS");}
|
||||
}
|
||||
}
|
||||
|
||||
private void render()
|
||||
{
|
||||
if( dbImage == null )
|
||||
{// create the buffer
|
||||
dbImage = createImage( pixelWidth, pixelHeight );
|
||||
if( dbImage == null )
|
||||
{
|
||||
System.out.println("dbImage is null???");
|
||||
return;
|
||||
}
|
||||
else
|
||||
{// dbg is created, tell Camera
|
||||
dbg = dbImage.getGraphics();
|
||||
Camera.setGraphicsContext( dbg );
|
||||
}
|
||||
}
|
||||
|
||||
// clear the background of entire window
|
||||
dbg.setColor( backgroundColor );
|
||||
dbg.fillRect(0,0,pixelWidth,pixelHeight);
|
||||
|
||||
// give app a chance to update its instance variables
|
||||
// and then draw stuff to dbg
|
||||
|
||||
step();
|
||||
}
|
||||
|
||||
private void paintScreen()
|
||||
{
|
||||
Graphics gr;
|
||||
try{
|
||||
gr = this.getGraphics();
|
||||
if( gr != null && dbImage != null )
|
||||
gr.drawImage(dbImage,0,0,null);
|
||||
Toolkit.getDefaultToolkit().sync(); // maybe not needed?
|
||||
gr.dispose();
|
||||
}
|
||||
catch(Exception e)
|
||||
{
|
||||
System.out.println("graphics context error" + e );
|
||||
System.exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
// override this method with code to display stuff
|
||||
// and update app instance variables
|
||||
public void step()
|
||||
{
|
||||
System.out.println("Step number: " + getStepNumber() );
|
||||
}
|
||||
|
||||
public int getStepNumber()
|
||||
{
|
||||
return stepNumber;
|
||||
}
|
||||
|
||||
// implement KeyListener:
|
||||
// ******************************************************************
|
||||
public void keyPressed(KeyEvent e){}
|
||||
public void keyReleased(KeyEvent e){}
|
||||
public void keyTyped(KeyEvent e){}
|
||||
|
||||
// implement MouseListener:
|
||||
// ******************************************************************
|
||||
public void mouseClicked(MouseEvent e)
|
||||
{
|
||||
updateMouse(e);
|
||||
}
|
||||
public void mouseEntered(MouseEvent e)
|
||||
{
|
||||
updateMouse(e);
|
||||
}
|
||||
public void mouseExited(MouseEvent e)
|
||||
{
|
||||
updateMouse(e);
|
||||
}
|
||||
public void mousePressed(MouseEvent e)
|
||||
{
|
||||
updateMouse(e);
|
||||
}
|
||||
public void mouseReleased(MouseEvent e)
|
||||
{
|
||||
updateMouse(e);
|
||||
}
|
||||
|
||||
// implement MouseMotionListener:
|
||||
// ******************************************************************
|
||||
public void mouseDragged(MouseEvent e)
|
||||
{
|
||||
updateMouse(e);
|
||||
}
|
||||
public void mouseMoved(MouseEvent e)
|
||||
{
|
||||
updateMouse(e);
|
||||
}
|
||||
|
||||
private void updateMouse( MouseEvent e )
|
||||
{
|
||||
int ix = e.getX(), iy = e.getY();
|
||||
|
||||
// determine which camera this mouse event hits
|
||||
// and compute mouseX, mouseY in that camera's graph paper coords
|
||||
|
||||
whichCamera = -1;
|
||||
Camera ac=null, temp;
|
||||
|
||||
for( int k=0; k<cameras.size(); k++ )
|
||||
{
|
||||
temp = cameras.get(k);
|
||||
if( temp.hits(ix,iy) )
|
||||
{
|
||||
ac = temp;
|
||||
whichCamera = k;
|
||||
}
|
||||
}
|
||||
|
||||
if( whichCamera == -1 )
|
||||
{
|
||||
mouseX=0; mouseY=0;
|
||||
whichCamera = -1;
|
||||
}
|
||||
else
|
||||
{// mouse event happened in an active camera, update coords for that cam
|
||||
mouseX = ac.invMapX( ix );
|
||||
mouseY = ac.invMapY( iy );
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------
|
||||
// These can be called, but don't override
|
||||
|
||||
protected double getMouseX()
|
||||
{
|
||||
return mouseX;
|
||||
}
|
||||
|
||||
protected double getMouseY()
|
||||
{
|
||||
return mouseY;
|
||||
}
|
||||
|
||||
protected int getMouseCamera()
|
||||
{
|
||||
return whichCamera;
|
||||
}
|
||||
|
||||
// set background color of entire window
|
||||
protected void setBackgroundColor( Color color )
|
||||
{
|
||||
backgroundColor = color;
|
||||
}
|
||||
|
||||
// implement WindowListener:
|
||||
// ******************************************************************^M
|
||||
public void windowActivated(WindowEvent e){}
|
||||
public void windowClosed(WindowEvent e){}
|
||||
public void windowClosing(WindowEvent e)
|
||||
{
|
||||
System.exit(0);
|
||||
} // end of windowClosing()
|
||||
public void windowDeactivated(WindowEvent e){}
|
||||
public void windowDeiconified(WindowEvent e){}
|
||||
public void windowIconified(WindowEvent e){}
|
||||
public void windowOpened(WindowEvent e){}
|
||||
|
||||
}
|
||||
Executable
+330
@@ -0,0 +1,330 @@
|
||||
import java.awt.*;
|
||||
import java.awt.font.FontRenderContext;
|
||||
import java.awt.font.GlyphVector;
|
||||
|
||||
public class Camera
|
||||
{
|
||||
// whenever graphics context is changed by Basic, all
|
||||
// cameras get shared access to that context
|
||||
// *******************************************************************
|
||||
|
||||
private static Graphics gc; // the graphics context
|
||||
|
||||
public static void setGraphicsContext( Graphics g )
|
||||
{
|
||||
gc = g;
|
||||
}
|
||||
|
||||
// instance variables
|
||||
// *******************************************************************
|
||||
|
||||
private Color backgroundColor;
|
||||
private int px, py, pw, ph; // the pixel grid rectangle where draw
|
||||
private double left, right, bottom, top; // the visible rectangle in the
|
||||
// virtual graph paper
|
||||
|
||||
private Font currentFont; // the current font
|
||||
private int currentFontHeight; // height of a typical char in current font
|
||||
|
||||
// methods for creating and changing camera properties
|
||||
// *******************************************************************
|
||||
|
||||
// construct a camera with both rectangles (pixelgrid and graph paper)
|
||||
// specified, and background color
|
||||
// Note: the top coordinate of the visible region is computed so that
|
||||
// the visible region has the same aspect ratio as the pixel
|
||||
// grid region (can change if desired by using setRegion)
|
||||
public Camera( int vx, int vy, int vw, int vh,
|
||||
double l, double r, double b,
|
||||
Color bc )
|
||||
{
|
||||
px=vx; py=vy; pw=vw; ph=vh;
|
||||
left=l; right=r; bottom=b; top=bottom + ph*(right-left)/pw;
|
||||
backgroundColor=bc;
|
||||
}
|
||||
|
||||
// construct a camera with both rectangles specified, and back color
|
||||
// Note: this constructor lets you select coordinates each way,
|
||||
// dangerous to draw geometrical entities
|
||||
public Camera( int vx, int vy, int vw, int vh,
|
||||
double l, double r, double b, double t,
|
||||
Color bc )
|
||||
{
|
||||
px=vx; py=vy; pw=vw; ph=vh;
|
||||
left=l; right=r; bottom=b; top=t;
|
||||
backgroundColor=bc;
|
||||
}
|
||||
// set the background color
|
||||
// (might want to change it after camera is first built)
|
||||
public void setBackgroundColor( Color color )
|
||||
{
|
||||
backgroundColor = color;
|
||||
}
|
||||
|
||||
// move the graph paper viewing rectangle
|
||||
public void setRegion( double l, double r, double b, double t )
|
||||
{
|
||||
left=l; right=r; bottom=b; top=t;
|
||||
}
|
||||
|
||||
// shift the graph paper rectangle by given fractions in x and y
|
||||
public void shiftRegion( double fx, double fy )
|
||||
{
|
||||
double dx = fx*(right-left);
|
||||
double dy = fy*(top-bottom);
|
||||
|
||||
left += dx; right += dx;
|
||||
bottom += dy; top += dy;
|
||||
}
|
||||
|
||||
// scale the graph paper rectangle by given fractions in x and y,
|
||||
// keeping the center fixed
|
||||
public void scaleRegion( double sx, double sy )
|
||||
{
|
||||
double cx = (left+right)/2, cy = (bottom+top)/2;
|
||||
|
||||
double dx = sx*(right-left);
|
||||
double dy = sy*(top-bottom);
|
||||
|
||||
left = cx - dx/2; right = cx + dx/2;
|
||||
bottom = cy - dy/2; top = cy + dy/2;
|
||||
}
|
||||
|
||||
public double getRegionLeft()
|
||||
{
|
||||
return left;
|
||||
}
|
||||
|
||||
public double getRegionBottom()
|
||||
{
|
||||
return bottom;
|
||||
}
|
||||
|
||||
public double getRegionWidth()
|
||||
{
|
||||
return right-left;
|
||||
}
|
||||
|
||||
public double getRegionHeight()
|
||||
{
|
||||
return top-bottom;
|
||||
}
|
||||
|
||||
// methods for drawing things used by application
|
||||
// *******************************************************************
|
||||
|
||||
// prepare pixel grid for this camera to draw in its region
|
||||
public void activate()
|
||||
{
|
||||
// set up clipping so no drawing can occur outside this camera's
|
||||
// pixel grid region
|
||||
gc.setClip(null);
|
||||
gc.clipRect( px, py, pw, ph );
|
||||
|
||||
// clear the background of entire window
|
||||
gc.setColor( backgroundColor );
|
||||
gc.fillRect( px, py, pw, ph );
|
||||
}
|
||||
|
||||
// set the drawing color
|
||||
public void setColor( Color color )
|
||||
{
|
||||
gc.setColor( color );
|
||||
}
|
||||
|
||||
// draw a rectangle---just the border---with lower left corner (x,y),
|
||||
// width w, height h, in graph paper coords
|
||||
public void drawRect( double x, double y, double w, double h )
|
||||
{
|
||||
rect( false, x, y, w, h );
|
||||
}
|
||||
|
||||
// draw a filled rectangle with lower left corner (x,y),
|
||||
// width w, height h, in graph paper coords
|
||||
public void fillRect( double x, double y, double w, double h )
|
||||
{
|
||||
rect( true, x, y, w, h );
|
||||
}
|
||||
|
||||
public void drawCircle( double x, double y, double r )
|
||||
{
|
||||
circle( false, x, y, r );
|
||||
}
|
||||
|
||||
public void fillCircle( double x, double y, double r )
|
||||
{
|
||||
circle( true, x, y, r );
|
||||
}
|
||||
|
||||
public void drawTri( double x1, double y1,
|
||||
double x2, double y2,
|
||||
double x3, double y3 )
|
||||
{
|
||||
tri( false, x1, y1, x2, y2, x3, y3 );
|
||||
}
|
||||
|
||||
public void fillTri( double x1, double y1,
|
||||
double x2, double y2,
|
||||
double x3, double y3 )
|
||||
{
|
||||
tri( true, x1, y1, x2, y2, x3, y3 );
|
||||
}
|
||||
|
||||
public void drawLine( double x1, double y1,
|
||||
double x2, double y2 )
|
||||
{
|
||||
gc.drawLine( mapX(x1), mapY(y1), mapX(x2), mapY(y2) );
|
||||
}
|
||||
|
||||
public void drawText( String text, double x, double y )
|
||||
{
|
||||
gc.drawString( text, mapX(x), mapY(y) );
|
||||
}
|
||||
|
||||
public void setFont( Font f )
|
||||
{
|
||||
currentFont = f;
|
||||
Rectangle r = figureBounds( "e", currentFont );
|
||||
currentFontHeight = r.height;
|
||||
|
||||
gc.setFont( f );
|
||||
}
|
||||
|
||||
// compute the width of the text in the current font
|
||||
// in the visible region
|
||||
public double getWidth( String text )
|
||||
{
|
||||
FontMetrics fm = gc.getFontMetrics();
|
||||
double w = invMapX( fm.stringWidth( text ) );
|
||||
return w;
|
||||
}
|
||||
|
||||
// compute the height of the current font
|
||||
// in the visible region
|
||||
public double getHeight()
|
||||
{
|
||||
FontMetrics fm = gc.getFontMetrics();
|
||||
double h = invMapY( fm.getHeight() );
|
||||
return h;
|
||||
}
|
||||
|
||||
// draw the text centered about (x,y)
|
||||
// using height of typical char (as in setFont) for vertical centering
|
||||
public void drawCenteredText( String text, double x, double y )
|
||||
{
|
||||
FontMetrics fm = gc.getFontMetrics();
|
||||
int w = fm.stringWidth( text );
|
||||
|
||||
gc.drawString( text, mapX(x)-w/2, mapY(y) + currentFontHeight/2 );
|
||||
}
|
||||
|
||||
// figure bounds of the given string
|
||||
private Rectangle figureBounds( String s, Font font )
|
||||
{
|
||||
Graphics2D g2 = (Graphics2D) gc;
|
||||
|
||||
g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
|
||||
RenderingHints.VALUE_ANTIALIAS_ON);
|
||||
|
||||
g2.setFont( font );
|
||||
|
||||
FontRenderContext frc = g2.getFontRenderContext();
|
||||
GlyphVector gv = g2.getFont().createGlyphVector(frc, s);
|
||||
|
||||
return gv.getPixelBounds(null, 0, 0);
|
||||
|
||||
}
|
||||
|
||||
// draw the text horizontally centered about x,
|
||||
// with baseline at y
|
||||
public void drawHorizCenteredText( String text, double x, double y )
|
||||
{
|
||||
FontMetrics fm = gc.getFontMetrics();
|
||||
int w = fm.stringWidth( text );
|
||||
|
||||
gc.drawString( text, mapX(x)-w/2, mapY(y) );
|
||||
}
|
||||
|
||||
// draw the text vertically centered about y,
|
||||
// with left edge at x
|
||||
public void drawVertCenteredText( String text, double x, double y )
|
||||
{
|
||||
gc.drawString( text, mapX(x), mapY(y) + currentFontHeight/2 );
|
||||
}
|
||||
|
||||
// use these carefully!
|
||||
// -----------------------------------------------------------------
|
||||
|
||||
public int mapX( double x )
|
||||
{
|
||||
return px + nicefy( ((x-left)/(right-left))*pw );
|
||||
}
|
||||
|
||||
public int mapY( double y )
|
||||
{
|
||||
return py + ph - nicefy( ((y-bottom)/(top-bottom))*ph );
|
||||
}
|
||||
|
||||
// does the mouse location in pixel grid (ix,iy) hit this
|
||||
// camera's pixel grid region
|
||||
public boolean hits( int ix, int iy )
|
||||
{
|
||||
boolean result = px<=ix && ix<=px+pw && py<=iy && iy<=py+ph;
|
||||
return result;
|
||||
}
|
||||
|
||||
public double invMapX( int ix )
|
||||
{
|
||||
return left + (right-left)*(ix-px)/pw;
|
||||
}
|
||||
|
||||
public double invMapY( int iy )
|
||||
{
|
||||
return bottom + (top-bottom)*(ph-(iy-py))/ph;
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------
|
||||
// methods used internally
|
||||
|
||||
private int nicefy( double a )
|
||||
{
|
||||
return (int) Math.round(a);
|
||||
}
|
||||
|
||||
// draw or fill a rectangle
|
||||
private void rect( boolean fill, double x, double y, double w, double h )
|
||||
{
|
||||
int x1, x2, y1, y2;
|
||||
x1 = mapX(x); x2 = mapX(x+w);
|
||||
y1 = mapY(y); y2 = mapY(y+h);
|
||||
|
||||
if( fill )
|
||||
gc.fillRect( x1, y2, x2-x1, y1-y2 );
|
||||
else
|
||||
gc.drawRect( x1, y2, x2-x1, y1-y2 );
|
||||
}
|
||||
|
||||
private void circle( boolean fill, double x, double y, double r )
|
||||
{
|
||||
int x1=mapX(x-r), y1=mapY(y+r), x2=mapX(x+r);
|
||||
|
||||
if( fill )
|
||||
gc.fillOval( x1, y1, x2-x1, x2-x1 );
|
||||
else
|
||||
gc.drawOval( x1, y1, x2-x1, x2-x1 );
|
||||
}
|
||||
|
||||
private void tri( boolean fill, double x1, double y1,
|
||||
double x2, double y2,
|
||||
double x3, double y3 )
|
||||
{
|
||||
int[] x = new int[3]; x[0]=mapX(x1); x[1]=mapX(x2); x[2]=mapX(x3);
|
||||
int[] y = new int[3]; y[0]=mapY(y1); y[1]=mapY(y2); y[2]=mapY(y3);
|
||||
|
||||
if( fill )
|
||||
gc.fillPolygon( x, y, 3 );
|
||||
else
|
||||
gc.drawPolygon( x, y, 3 );
|
||||
}
|
||||
|
||||
}
|
||||
Executable
+25
@@ -0,0 +1,25 @@
|
||||
import java.util.Scanner;
|
||||
|
||||
public class Corgi {
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
System.out.print("Enter name of Corgi program file: ");
|
||||
Scanner keys = new Scanner( System.in );
|
||||
String name = keys.nextLine();
|
||||
|
||||
Lexer lex = new Lexer( name );
|
||||
Parser parser = new Parser( lex );
|
||||
|
||||
// start with <statements>
|
||||
Node root = parser.parseProgram();
|
||||
|
||||
// display parse tree for debugging/testing:
|
||||
TreeViewer viewer = new TreeViewer("Parse Tree", 0, 0, 800, 500, root );
|
||||
|
||||
// execute the parse tree
|
||||
// root.execute();
|
||||
|
||||
}// main
|
||||
|
||||
}
|
||||
Executable
+275
@@ -0,0 +1,275 @@
|
||||
import java.io.BufferedReader;
|
||||
import java.io.FileReader;
|
||||
import java.util.Scanner;
|
||||
import java.util.Stack;
|
||||
public class Lexer {
|
||||
|
||||
public static String margin = "";
|
||||
|
||||
// holds any number of tokens that have been put back
|
||||
private Stack<Token> stack;
|
||||
|
||||
// the source of physical symbols
|
||||
// (use BufferedReader instead of Scanner because it can
|
||||
// read a single physical symbol)
|
||||
private BufferedReader input;
|
||||
|
||||
// one lookahead physical symbol
|
||||
private int lookahead;
|
||||
|
||||
// construct a Lexer ready to produce tokens from a file
|
||||
public Lexer( String fileName ) {
|
||||
try {
|
||||
input = new BufferedReader( new FileReader( fileName ) );
|
||||
}
|
||||
catch(Exception e) {
|
||||
error("Problem opening file named [" + fileName + "]" );
|
||||
}
|
||||
stack = new Stack<Token>();
|
||||
lookahead = 0; // indicates no lookahead symbol present
|
||||
}// constructor
|
||||
|
||||
// produce the next token
|
||||
private Token getNext() {
|
||||
if( ! stack.empty() ) {
|
||||
// produce the most recently putback token
|
||||
Token token = stack.pop();
|
||||
return token;
|
||||
}
|
||||
else {
|
||||
// produce a token from the input source
|
||||
|
||||
int state = 1; // state of FA
|
||||
String data = ""; // specific info for the token
|
||||
boolean done = false;
|
||||
int sym; // holds current symbol
|
||||
|
||||
do {
|
||||
sym = getNextSymbol();
|
||||
|
||||
// System.out.println("current symbol: " + sym + " state = " + state );
|
||||
|
||||
if ( state == 1 ) {
|
||||
if ( sym == 9 || sym == 10 || sym == 13 ||
|
||||
sym == 32 ) {// whitespace
|
||||
state = 1;
|
||||
}
|
||||
else if ( 'a'<=sym && sym<='z' ) {// lowercase
|
||||
data += (char) sym;
|
||||
state = 2;
|
||||
}
|
||||
else if ( digit( sym ) ) {
|
||||
data += (char) sym;
|
||||
state = 3;
|
||||
}
|
||||
else if ( sym == '.' ) {
|
||||
data += (char) sym;
|
||||
state = 5;
|
||||
}
|
||||
else if ( sym == '\"' ) {
|
||||
state = 6;
|
||||
}
|
||||
else if ( sym == '+' || sym == '-' || sym == '*' ||
|
||||
sym == '/' || sym == '(' || sym == ')' ||
|
||||
sym == ',' || sym == '='
|
||||
) {
|
||||
data += (char) sym;
|
||||
state = 8;
|
||||
done = true;
|
||||
}
|
||||
else if ( sym == -1 ) {// end of file
|
||||
state = 9;
|
||||
done = true;
|
||||
}
|
||||
else {
|
||||
error("Error in lexical analysis phase with symbol "
|
||||
+ sym + " in state " + state );
|
||||
}
|
||||
}
|
||||
|
||||
else if ( state == 2 ) {
|
||||
if ( letter(sym) || digit(sym) ) {
|
||||
data += (char) sym;
|
||||
state = 2;
|
||||
}
|
||||
else {// done with variable token
|
||||
putBackSymbol( sym );
|
||||
done = true;
|
||||
}
|
||||
}
|
||||
|
||||
else if ( state == 3 ) {
|
||||
if ( digit(sym) ) {
|
||||
data += (char) sym;
|
||||
state = 3;
|
||||
}
|
||||
else if ( sym == '.' ) {
|
||||
data += (char) sym;
|
||||
state = 4;
|
||||
}
|
||||
else {// done with number token
|
||||
putBackSymbol( sym );
|
||||
done = true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
else if ( state == 4 ) {
|
||||
if ( digit(sym) ) {
|
||||
data += (char) sym;
|
||||
state = 4;
|
||||
}
|
||||
else {// done with number token
|
||||
putBackSymbol( sym );
|
||||
done = true;
|
||||
}
|
||||
}
|
||||
|
||||
else if ( state == 5 ) {
|
||||
if ( digit(sym) ) {
|
||||
data += (char) sym;
|
||||
state = 4;
|
||||
}
|
||||
else {
|
||||
error("Error in lexical analysis phase with symbol "
|
||||
+ sym + " in state " + state );
|
||||
}
|
||||
}
|
||||
|
||||
else if ( state == 6 ) {
|
||||
if ( (' '<=sym && sym<='~') && sym != '\"' ) {
|
||||
data += (char) sym;
|
||||
state = 6;
|
||||
}
|
||||
else if ( sym == '\"' ) {
|
||||
state = 7;
|
||||
done = true;
|
||||
}
|
||||
}
|
||||
|
||||
// note: states 7, 8, and 9 are accepting states with
|
||||
// no arcs out of them, so they are handled
|
||||
// in the arc going into them
|
||||
}while( !done );
|
||||
|
||||
// generate token depending on stopping state
|
||||
Token token;
|
||||
|
||||
if ( state == 2 ) {
|
||||
// see if data matches any special words
|
||||
if ( data.equals("input") ) {
|
||||
return new Token( "bif0", data );
|
||||
}
|
||||
else if ( data.equals("sqrt") || data.equals("cos") ||
|
||||
data.equals("sin") || data.equals("atan")
|
||||
) {
|
||||
return new Token( "bif1", data );
|
||||
}
|
||||
else if ( data.equals("pow") ) {
|
||||
return new Token( "bif2", data );
|
||||
}
|
||||
else if ( data.equals("print") ) {
|
||||
return new Token( "print", "" );
|
||||
}
|
||||
else if ( data.equals("newline") ) {
|
||||
return new Token( "newline", "" );
|
||||
}
|
||||
else {// is just a variable
|
||||
return new Token( "var", data );
|
||||
}
|
||||
}
|
||||
else if ( state == 3 || state == 4 ) {
|
||||
return new Token( "num", data );
|
||||
}
|
||||
else if ( state == 7 ) {
|
||||
return new Token( "string", data );
|
||||
}
|
||||
else if ( state == 8 ) {
|
||||
return new Token( "single", data );
|
||||
}
|
||||
else if ( state == 9 ) {
|
||||
return new Token( "eof", data );
|
||||
}
|
||||
|
||||
else {// Lexer error
|
||||
error("somehow Lexer FA halted in bad state " + state );
|
||||
return null;
|
||||
}
|
||||
|
||||
}// else generate token from input
|
||||
|
||||
}// getNext
|
||||
|
||||
public Token getNextToken() {
|
||||
Token token = getNext();
|
||||
System.out.println(" got token: " + token );
|
||||
return token;
|
||||
}
|
||||
|
||||
public void putBackToken( Token token )
|
||||
{
|
||||
System.out.println( margin + "put back token " + token.toString() );
|
||||
stack.push( token );
|
||||
}
|
||||
|
||||
// next physical symbol is the lookahead symbol if there is one,
|
||||
// otherwise is next symbol from file
|
||||
private int getNextSymbol() {
|
||||
int result = -1;
|
||||
|
||||
if( lookahead == 0 ) {// is no lookahead, use input
|
||||
try{ result = input.read(); }
|
||||
catch(Exception e){}
|
||||
}
|
||||
else {// use the lookahead and consume it
|
||||
result = lookahead;
|
||||
lookahead = 0;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
private void putBackSymbol( int sym ) {
|
||||
if( lookahead == 0 ) {// sensible to put one back
|
||||
lookahead = sym;
|
||||
}
|
||||
else {
|
||||
System.out.println("Oops, already have a lookahead " + lookahead +
|
||||
" when trying to put back symbol " + sym );
|
||||
System.exit(1);
|
||||
}
|
||||
}// putBackSymbol
|
||||
|
||||
private boolean letter( int code ) {
|
||||
return 'a'<=code && code<='z' ||
|
||||
'A'<=code && code<='Z';
|
||||
}
|
||||
|
||||
private boolean digit( int code ) {
|
||||
return '0'<=code && code<='9';
|
||||
}
|
||||
|
||||
private boolean printable( int code ) {
|
||||
return ' '<=code && code<='~';
|
||||
}
|
||||
|
||||
private static void error( String message ) {
|
||||
System.out.println( message );
|
||||
System.exit(1);
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
System.out.print("Enter file name: ");
|
||||
Scanner keys = new Scanner( System.in );
|
||||
String name = keys.nextLine();
|
||||
|
||||
Lexer lex = new Lexer( name );
|
||||
Token token;
|
||||
|
||||
do{
|
||||
token = lex.getNext();
|
||||
System.out.println( token.toString() );
|
||||
}while( ! token.getKind().equals( "eof" ) );
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
Executable
+75
@@ -0,0 +1,75 @@
|
||||
/*
|
||||
store variable names with stored value
|
||||
*/
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
public class MemTable {
|
||||
|
||||
private ArrayList<String> names;
|
||||
private ArrayList<Double> values;
|
||||
|
||||
public MemTable() {
|
||||
names = new ArrayList<String>();
|
||||
values = new ArrayList<Double>();
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
String s = "----\n";
|
||||
for( int k=0; k<names.size(); k++ ) {
|
||||
s += names.get(k) + " " + values.get(k) + "\n";
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
public int size() {
|
||||
return names.size();
|
||||
}
|
||||
|
||||
// store value for name, adding name if not already
|
||||
// there
|
||||
public void store( String name, double value ) {
|
||||
|
||||
int loc = findName( name );
|
||||
|
||||
if ( loc < 0 ) {// add new pair
|
||||
names.add( name );
|
||||
values.add( value );
|
||||
}
|
||||
else {// change value for existing pair
|
||||
values.set( loc, value );
|
||||
}
|
||||
|
||||
}// store
|
||||
|
||||
// retrieve value for given name
|
||||
public double retrieve( String name ) {
|
||||
|
||||
int loc = findName( name );
|
||||
|
||||
if ( loc >= 0 ) {// add new pair
|
||||
return values.get( loc );
|
||||
}
|
||||
else {
|
||||
System.out.println("variable [" + name + "] not found");
|
||||
System.exit(1);
|
||||
return 0;
|
||||
}
|
||||
|
||||
}// retrieve
|
||||
|
||||
// return index of name in names, or -1 if
|
||||
// not found
|
||||
private int findName( String name ) {
|
||||
// locate name
|
||||
int loc = -1;
|
||||
for (int k=0; k<names.size() && loc<0; k++) {
|
||||
if ( names.get(k).equals(name) ) {
|
||||
loc = k;
|
||||
}
|
||||
}
|
||||
|
||||
return loc;
|
||||
}// findName
|
||||
|
||||
}
|
||||
Executable
+223
@@ -0,0 +1,223 @@
|
||||
/* a Node holds one node of a parse tree
|
||||
with several pointers to children used
|
||||
depending on the kind of node
|
||||
*/
|
||||
|
||||
import java.awt.*;
|
||||
import java.util.Scanner;
|
||||
|
||||
public class Node {
|
||||
|
||||
public static int count = 0; // maintain unique id for each node
|
||||
|
||||
private int id;
|
||||
|
||||
private String kind; // non-terminal or terminal category for the node
|
||||
private String info; // extra information about the node such as
|
||||
// the actual identifier for an I
|
||||
|
||||
// references to children in the parse tree
|
||||
private Node first, second, third;
|
||||
|
||||
// memory table shared by all nodes
|
||||
private static MemTable table = new MemTable();
|
||||
|
||||
private static Scanner keys = new Scanner( System.in );
|
||||
|
||||
// construct a common node with no info specified
|
||||
public Node( String k, Node one, Node two, Node three ) {
|
||||
kind = k; info = "";
|
||||
first = one; second = two; third = three;
|
||||
id = count;
|
||||
count++;
|
||||
System.out.println( this );
|
||||
}
|
||||
|
||||
// construct a node with specified info
|
||||
public Node( String k, String inf, Node one, Node two, Node three ) {
|
||||
kind = k; info = inf;
|
||||
first = one; second = two; third = three;
|
||||
id = count;
|
||||
count++;
|
||||
System.out.println( this );
|
||||
}
|
||||
|
||||
// construct a node that is essentially a token
|
||||
public Node( Token token ) {
|
||||
kind = token.getKind(); info = token.getDetails();
|
||||
first = null; second = null; third = null;
|
||||
id = count;
|
||||
count++;
|
||||
System.out.println( this );
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return "#" + id + "[" + kind + "," + info + "]<" + nice(first) +
|
||||
" " + nice(second) + ">";
|
||||
}
|
||||
|
||||
public String nice( Node node ) {
|
||||
if ( node == null ) {
|
||||
return "";
|
||||
}
|
||||
else {
|
||||
return "" + node.id;
|
||||
}
|
||||
}
|
||||
|
||||
// produce array with the non-null children
|
||||
// in order
|
||||
private Node[] getChildren() {
|
||||
int count = 0;
|
||||
if( first != null ) count++;
|
||||
if( second != null ) count++;
|
||||
if( third != null ) count++;
|
||||
Node[] children = new Node[count];
|
||||
int k=0;
|
||||
if( first != null ) { children[k] = first; k++; }
|
||||
if( second != null ) { children[k] = second; k++; }
|
||||
if( third != null ) { children[k] = third; k++; }
|
||||
|
||||
return children;
|
||||
}
|
||||
|
||||
//******************************************************
|
||||
// graphical display of this node and its subtree
|
||||
// in given camera, with specified location (x,y) of this
|
||||
// node, and specified distances horizontally and vertically
|
||||
// to children
|
||||
public void draw( Camera cam, double x, double y, double h, double v ) {
|
||||
|
||||
System.out.println("draw node " + id );
|
||||
|
||||
// set drawing color
|
||||
cam.setColor( Color.black );
|
||||
|
||||
String text = kind;
|
||||
if( ! info.equals("") ) text += "(" + info + ")";
|
||||
cam.drawHorizCenteredText( text, x, y );
|
||||
|
||||
// positioning of children depends on how many
|
||||
// in a nice, uniform manner
|
||||
Node[] children = getChildren();
|
||||
int number = children.length;
|
||||
System.out.println("has " + number + " children");
|
||||
|
||||
double top = y - 0.75*v;
|
||||
|
||||
if( number == 0 ) {
|
||||
return;
|
||||
}
|
||||
else if( number == 1 ) {
|
||||
children[0].draw( cam, x, y-v, h/2, v ); cam.drawLine( x, y, x, top );
|
||||
}
|
||||
else if( number == 2 ) {
|
||||
children[0].draw( cam, x-h/2, y-v, h/2, v ); cam.drawLine( x, y, x-h/2, top );
|
||||
children[1].draw( cam, x+h/2, y-v, h/2, v ); cam.drawLine( x, y, x+h/2, top );
|
||||
}
|
||||
else if( number == 3 ) {
|
||||
children[0].draw( cam, x-h, y-v, h/2, v ); cam.drawLine( x, y, x-h, top );
|
||||
children[1].draw( cam, x, y-v, h/2, v ); cam.drawLine( x, y, x, top );
|
||||
children[2].draw( cam, x+h, y-v, h/2, v ); cam.drawLine( x, y, x+h, top );
|
||||
}
|
||||
else {
|
||||
System.out.println("no Node kind has more than 3 children???");
|
||||
System.exit(1);
|
||||
}
|
||||
|
||||
}// draw
|
||||
|
||||
public static void error( String message ) {
|
||||
System.out.println( message );
|
||||
System.exit(1);
|
||||
}
|
||||
|
||||
// ask this node to execute itself
|
||||
// (for nodes that don't return a value)
|
||||
public void execute() {
|
||||
|
||||
if ( kind.equals("stmts") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("prtstr") ) {
|
||||
System.out.print( info );
|
||||
}
|
||||
|
||||
else if ( kind.equals("prtexp") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("nl") ) {
|
||||
System.out.print( "\n" );
|
||||
}
|
||||
|
||||
else if ( kind.equals("sto") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else {
|
||||
error("Unknown kind of node [" + kind + "]");
|
||||
}
|
||||
|
||||
}// execute
|
||||
|
||||
// compute and return value produced by this node
|
||||
public double evaluate() {
|
||||
|
||||
if ( kind.equals("num") ) {
|
||||
return Double.parseDouble( info );
|
||||
}
|
||||
|
||||
else if ( kind.equals("var") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("+") || kind.equals("-") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("*") || kind.equals("/") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("input") ) {
|
||||
return keys.nextDouble();
|
||||
}
|
||||
|
||||
else if ( kind.equals("sqrt") || kind.equals("cos") ||
|
||||
kind.equals("sin") || kind.equals("atan")
|
||||
) {
|
||||
double value = first.evaluate();
|
||||
|
||||
if ( kind.equals("sqrt") )
|
||||
return Math.sqrt(value);
|
||||
else if ( kind.equals("cos") )
|
||||
return Math.cos( Math.toRadians( value ) );
|
||||
else if ( kind.equals("sin") )
|
||||
return Math.sin( Math.toRadians( value ) );
|
||||
else if ( kind.equals("atan") )
|
||||
return Math.toDegrees( Math.atan( value ) );
|
||||
else {
|
||||
error("unknown function name [" + kind + "]");
|
||||
return 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
else if ( kind.equals("pow") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("opp") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else {
|
||||
error("Unknown node kind [" + kind + "]");
|
||||
return 0;
|
||||
}
|
||||
|
||||
}// evaluate
|
||||
|
||||
}// Node
|
||||
Executable
+202
@@ -0,0 +1,202 @@
|
||||
/*
|
||||
This class provides a recursive descent parser
|
||||
for Corgi (a simple calculator language),
|
||||
creating a parse tree which can be interpreted
|
||||
to simulate execution of a Corgi program
|
||||
*/
|
||||
|
||||
public class Parser {
|
||||
|
||||
private Lexer lex;
|
||||
|
||||
public Parser( Lexer lexer ) {
|
||||
lex = lexer;
|
||||
}
|
||||
|
||||
public Node parseProgram() {
|
||||
return parseStatements();
|
||||
}
|
||||
|
||||
private Node parseStatements() {
|
||||
System.out.println("-----> parsing <statements>:");
|
||||
|
||||
Node first = parseStatement();
|
||||
|
||||
// look ahead to see if there are more statement's
|
||||
Token token = lex.getNextToken();
|
||||
|
||||
if ( token.isKind("eof") ) {
|
||||
return new Node( "stmts", first, null, null );
|
||||
}
|
||||
else {
|
||||
lex.putBackToken( token );
|
||||
Node second = parseStatements();
|
||||
return new Node( "stmts", first, second, null );
|
||||
}
|
||||
}// <statements>
|
||||
|
||||
private Node parseStatement() {
|
||||
System.out.println("-----> parsing <statement>:");
|
||||
|
||||
Token token = lex.getNextToken();
|
||||
|
||||
// ---------------->>> print <string> or print <expr>
|
||||
if ( token.isKind("print") ) {
|
||||
token = lex.getNextToken();
|
||||
|
||||
if ( token.isKind("string") ) {// print <string>
|
||||
return new Node( "prtstr", token.getDetails(),
|
||||
null, null, null );
|
||||
}
|
||||
else {// must be first token in <expr>
|
||||
// put back the token we looked ahead at
|
||||
lex.putBackToken( token );
|
||||
Node first = parseExpr();
|
||||
return new Node( "prtexp", first, null, null );
|
||||
}
|
||||
// ---------------->>> newline
|
||||
}
|
||||
else if ( token.isKind("newline") ) {
|
||||
return new Node( "nl", null, null, null );
|
||||
}
|
||||
// --------------->>> <var> = <expr>
|
||||
else if ( token.isKind("var") ) {
|
||||
String varName = token.getDetails();
|
||||
token = lex.getNextToken();
|
||||
errorCheck( token, "single", "=" );
|
||||
Node first = parseExpr();
|
||||
return new Node( "sto", varName, first, null, null );
|
||||
}
|
||||
else {
|
||||
System.out.println("Token " + token +
|
||||
" can't begin a statement");
|
||||
System.exit(1);
|
||||
return null;
|
||||
}
|
||||
|
||||
}// <statement>
|
||||
|
||||
private Node parseExpr() {
|
||||
System.out.println("-----> parsing <expr>");
|
||||
|
||||
Node first = parseTerm();
|
||||
|
||||
// look ahead to see if there's an addop
|
||||
Token token = lex.getNextToken();
|
||||
|
||||
if ( token.matches("single", "+") ||
|
||||
token.matches("single", "-")
|
||||
) {
|
||||
Node second = parseExpr();
|
||||
return new Node( token.getDetails(), first, second, null );
|
||||
}
|
||||
else {// is just one term
|
||||
lex.putBackToken( token );
|
||||
return first;
|
||||
}
|
||||
|
||||
}// <expr>
|
||||
|
||||
private Node parseTerm() {
|
||||
System.out.println("-----> parsing <term>");
|
||||
|
||||
Node first = parseFactor();
|
||||
|
||||
// look ahead to see if there's a multop
|
||||
Token token = lex.getNextToken();
|
||||
|
||||
if ( token.matches("single", "*") ||
|
||||
token.matches("single", "/")
|
||||
) {
|
||||
Node second = parseTerm();
|
||||
return new Node( token.getDetails(), first, second, null );
|
||||
}
|
||||
else {// is just one factor
|
||||
lex.putBackToken( token );
|
||||
return first;
|
||||
}
|
||||
|
||||
}// <term>
|
||||
|
||||
private Node parseFactor() {
|
||||
System.out.println("-----> parsing <factor>");
|
||||
|
||||
Token token = lex.getNextToken();
|
||||
|
||||
if ( token.isKind("num") ) {
|
||||
return new Node("num", token.getDetails(), null, null, null );
|
||||
}
|
||||
else if ( token.isKind("var") ) {
|
||||
return new Node("var", token.getDetails(), null, null, null );
|
||||
}
|
||||
else if ( token.matches("single","(") ) {
|
||||
Node first = parseExpr();
|
||||
token = lex.getNextToken();
|
||||
errorCheck( token, "single", ")" );
|
||||
return first;
|
||||
}
|
||||
else if ( token.isKind("bif0") ) {
|
||||
String bifName = token.getDetails();
|
||||
token = lex.getNextToken();
|
||||
errorCheck( token, "single", "(" );
|
||||
token = lex.getNextToken();
|
||||
errorCheck( token, "single", ")" );
|
||||
|
||||
return new Node( bifName, null, null, null );
|
||||
}
|
||||
else if ( token.isKind("bif1") ) {
|
||||
String bifName = token.getDetails();
|
||||
token = lex.getNextToken();
|
||||
errorCheck( token, "single", "(" );
|
||||
Node first = parseExpr();
|
||||
token = lex.getNextToken();
|
||||
errorCheck( token, "single", ")" );
|
||||
|
||||
return new Node( bifName, first, null, null );
|
||||
}
|
||||
else if ( token.isKind("bif2") ) {
|
||||
String bifName = token.getDetails();
|
||||
token = lex.getNextToken();
|
||||
errorCheck( token, "single", "(" );
|
||||
Node first = parseExpr();
|
||||
token = lex.getNextToken();
|
||||
errorCheck( token, "single", "," );
|
||||
Node second = parseExpr();
|
||||
token = lex.getNextToken();
|
||||
errorCheck( token, "single", ")" );
|
||||
|
||||
return new Node( bifName, first, second, null );
|
||||
}
|
||||
else if ( token.matches("single","-") ) {
|
||||
Node first = parseFactor();
|
||||
return new Node("opp", first, null, null );
|
||||
}
|
||||
else {
|
||||
System.out.println("Can't have factor starting with " + token );
|
||||
System.exit(1);
|
||||
return null;
|
||||
}
|
||||
|
||||
}// <factor>
|
||||
|
||||
// check whether token is correct kind
|
||||
private void errorCheck( Token token, String kind ) {
|
||||
if( ! token.isKind( kind ) ) {
|
||||
System.out.println("Error: expected " + token +
|
||||
" to be of kind " + kind );
|
||||
System.exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
// check whether token is correct kind and details
|
||||
private void errorCheck( Token token, String kind, String details ) {
|
||||
if( ! token.isKind( kind ) ||
|
||||
! token.getDetails().equals( details ) ) {
|
||||
System.out.println("Error: expected " + token +
|
||||
" to be kind=" + kind +
|
||||
" and details=" + details );
|
||||
System.exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
Executable
+20
@@ -0,0 +1,20 @@
|
||||
main()
|
||||
|
||||
def fact( n )
|
||||
|
||||
if lt(n 1)
|
||||
return 1
|
||||
else
|
||||
temp = fact( n-1 )
|
||||
return n * temp
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
def main()
|
||||
|
||||
"enter n: "
|
||||
n = input()
|
||||
print( fact(n) )
|
||||
|
||||
end
|
||||
Executable
+23
@@ -0,0 +1,23 @@
|
||||
main()
|
||||
|
||||
def main()
|
||||
|
||||
"enter a:"
|
||||
|
||||
a = input()
|
||||
|
||||
"enter b:"
|
||||
b = input()
|
||||
|
||||
"enter c:"
|
||||
c = input()
|
||||
|
||||
disc = pow(b,2) - 4*a*c
|
||||
|
||||
x1 = (-b - sqrt(disc) ) / (2*a)
|
||||
x2 = (-b + sqrt(disc) ) / (2*a)
|
||||
|
||||
"x1: " print(x1) "\n"
|
||||
"x2: " print(x2 ) "\n"
|
||||
|
||||
end
|
||||
Executable
+31
@@ -0,0 +1,31 @@
|
||||
public class Token
|
||||
{
|
||||
private String kind;
|
||||
private String details;
|
||||
|
||||
public Token( String k, String d )
|
||||
{
|
||||
kind = k; details = d;
|
||||
}
|
||||
|
||||
public boolean isKind( String s )
|
||||
{
|
||||
return kind.equals( s );
|
||||
}
|
||||
|
||||
public String getKind()
|
||||
{ return kind; }
|
||||
|
||||
public String getDetails()
|
||||
{ return details; }
|
||||
|
||||
public boolean matches( String k, String d ) {
|
||||
return kind.equals(k) && details.equals(d);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "[" + kind + "," + details + "]";
|
||||
}
|
||||
|
||||
}
|
||||
Executable
+78
@@ -0,0 +1,78 @@
|
||||
/* this class allows interactive
|
||||
viewing of a tree built from
|
||||
Node instances
|
||||
*/
|
||||
|
||||
import java.awt.*;
|
||||
import java.awt.event.KeyEvent;
|
||||
|
||||
public class TreeViewer extends Basic
|
||||
{
|
||||
// instance variables for the application:
|
||||
// vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv
|
||||
|
||||
private Node root; // root of tree to be viewed
|
||||
|
||||
private String keyInput;
|
||||
private double horizGap = 2, vertGap = .5;
|
||||
|
||||
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
public TreeViewer( String title, int ulx, int uly, int pw, int ph,
|
||||
Node tree )
|
||||
{
|
||||
super(title,ulx,uly,pw,ph);
|
||||
|
||||
setBackgroundColor( new Color( 128, 128, 200 ) );
|
||||
|
||||
// tree display
|
||||
cameras.add( new Camera( 25, 45, pw-55, ph-75,
|
||||
0, 10, 0, 5,
|
||||
new Color( 200, 200, 200 ) ) );
|
||||
|
||||
root = tree;
|
||||
|
||||
super.start();
|
||||
}
|
||||
|
||||
public void step()
|
||||
{
|
||||
// tree display
|
||||
Camera cam = cameras.get(0);
|
||||
cam.activate();
|
||||
cam.setColor( Color.black );
|
||||
|
||||
root.draw( cam, 5.0, 4.0, horizGap, vertGap );
|
||||
|
||||
}// step
|
||||
|
||||
public void keyTyped( KeyEvent e ) {
|
||||
char key = e.getKeyChar();
|
||||
|
||||
if( key == 'w' ){
|
||||
horizGap *= 1.2;
|
||||
}
|
||||
else if( key == 'n' ){
|
||||
horizGap /= 1.2;
|
||||
}
|
||||
|
||||
}// keyTyped
|
||||
|
||||
public void keyPressed( KeyEvent e ) {
|
||||
int code = e.getKeyCode();
|
||||
|
||||
if( code == KeyEvent.VK_LEFT ){
|
||||
cameras.get(0).shiftRegion( -0.25, 0 );
|
||||
}
|
||||
else if( code == KeyEvent.VK_RIGHT ){
|
||||
cameras.get(0).shiftRegion( 0.25, 0 );
|
||||
}
|
||||
else if( code == KeyEvent.VK_UP ){
|
||||
cameras.get(0).shiftRegion( 0, 0.25 );
|
||||
}
|
||||
else if( code == KeyEvent.VK_DOWN ){
|
||||
cameras.get(0).shiftRegion( 0, -0.25 );
|
||||
}
|
||||
}// keyPressed
|
||||
|
||||
}// TreeViewer
|
||||
Executable
+66
@@ -0,0 +1,66 @@
|
||||
Note: this is the draft grammar, with notes and some thoughts,
|
||||
for the Project 2 version of Corgi
|
||||
------------------
|
||||
|
||||
<program> -> <funcCall> <funcDefs>
|
||||
|
||||
<funcDefs> -> <funcDef> | <funcDef> <funcDefs>
|
||||
|
||||
<funcDef> -> def <funcName> ( ) end |
|
||||
def <funcName> ( <params> ) end |
|
||||
def <funcName> ( ) <statements> end
|
||||
def <funcName> ( <params> ) <statements> end
|
||||
|
||||
<funcName> -> <var>
|
||||
|
||||
<params> -> <var> | <var> <params>
|
||||
|
||||
<statements> -> <statement> |
|
||||
<statement> <statements>
|
||||
|
||||
<funcCall> -> <var> ( ) |
|
||||
<var> ( <args> )
|
||||
|
||||
<args> -> <expr> | <expr> <args>
|
||||
|
||||
<statement> -> <string> |
|
||||
<var> = <expr> |
|
||||
<funcCall> |
|
||||
if <expr> else end |
|
||||
if <expr> else <statements> end |
|
||||
if <expr> <statements> else end |
|
||||
if <expr> <statements> else <statements> end |
|
||||
return <expr>
|
||||
|
||||
<expr> -> <term> | <term> + <expr> | <term> - <expr>
|
||||
<term> -> <factor> | <factor> * <term> | <factor> / <term>
|
||||
|
||||
<factor> -> <number> | <var> |
|
||||
( <expr> ) |
|
||||
- <factor> |
|
||||
<funcCall>
|
||||
|
||||
|
||||
Notes:
|
||||
|
||||
slightly bizarre but cool: in Corgi you can just type a string anywhere
|
||||
as a statement and it gets sent to the console (still have to use
|
||||
print( <expr> ) to send a number)
|
||||
|
||||
no boolean type---use "non-zero is true, 0 is false"
|
||||
|
||||
there's only the if-else---always have to use it
|
||||
|
||||
no loop statements---use recursion!
|
||||
|
||||
the built-in functions fit the grammar just like user-defined functions---
|
||||
will execute differently
|
||||
|
||||
change the Lexer to remove /* ..... */ type of comments---no tokens
|
||||
produced
|
||||
|
||||
change Lexer to allow \n inside a string---put \\ in the Java string
|
||||
|
||||
|
||||
Need to agree on names for all the many BIF's---see upcoming document
|
||||
|
||||
Executable
+19
@@ -0,0 +1,19 @@
|
||||
<program> -> <statements>
|
||||
|
||||
<statements> -> <statement> |
|
||||
<statement> <statements>
|
||||
|
||||
<statement> -> print <string> |
|
||||
print <expr> |
|
||||
newline |
|
||||
<var> = <expr>
|
||||
|
||||
<expr> -> <term> | <term> <addop> <expr>
|
||||
<term> -> <factor> | <factor> <multop> <term>
|
||||
|
||||
<factor> -> <number> | <var> |
|
||||
( <expr> ) |
|
||||
<bif0> () |
|
||||
<bif1> ( <expr> ) |
|
||||
<bif2> ( <expr>, <expr> ) |
|
||||
- <factor>
|
||||
Executable
+87
@@ -0,0 +1,87 @@
|
||||
// ask this node to execute itself
|
||||
// (for nodes that don't return a value)
|
||||
public void execute() {
|
||||
|
||||
if ( kind.equals("stmts") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("prtstr") ) {
|
||||
System.out.print( info );
|
||||
}
|
||||
|
||||
else if ( kind.equals("prtexp") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("nl") ) {
|
||||
System.out.print( "\n" );
|
||||
}
|
||||
|
||||
else if ( kind.equals("sto") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else {
|
||||
error("Unknown kind of node [" + kind + "]");
|
||||
}
|
||||
|
||||
}// execute
|
||||
|
||||
// compute and return value produced by this node
|
||||
public double evaluate() {
|
||||
|
||||
if ( kind.equals("num") ) {
|
||||
return Double.parseDouble( info );
|
||||
}
|
||||
|
||||
else if ( kind.equals("var") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("+") || kind.equals("-") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("*") || kind.equals("/") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("input") ) {
|
||||
return keys.nextDouble();
|
||||
}
|
||||
|
||||
else if ( kind.equals("sqrt") || kind.equals("cos") ||
|
||||
kind.equals("sin") || kind.equals("atan")
|
||||
) {
|
||||
double value = first.evaluate();
|
||||
|
||||
if ( kind.equals("sqrt") )
|
||||
return Math.sqrt(value);
|
||||
else if ( kind.equals("cos") )
|
||||
return Math.cos( Math.toRadians( value ) );
|
||||
else if ( kind.equals("sin") )
|
||||
return Math.sin( Math.toRadians( value ) );
|
||||
else if ( kind.equals("atan") )
|
||||
return Math.toDegrees( Math.atan( value ) );
|
||||
else {
|
||||
error("unknown function name [" + kind + "]");
|
||||
return 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
else if ( kind.equals("pow") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else if ( kind.equals("opp") ) {
|
||||
// insert code here for Exercise 15
|
||||
}
|
||||
|
||||
else {
|
||||
error("Unknown node kind [" + kind + "]");
|
||||
return 0;
|
||||
}
|
||||
|
||||
}// evaluate
|
||||
Executable
+16
@@ -0,0 +1,16 @@
|
||||
print "enter a:"
|
||||
|
||||
a = input()
|
||||
|
||||
print "enter b:"
|
||||
b = input()
|
||||
print "enter c:"
|
||||
c = input()
|
||||
|
||||
disc = pow(b,2) - 4*a*c
|
||||
|
||||
x1 = (-b - sqrt(disc) ) / (2*a)
|
||||
x2 = (-b + sqrt(disc) ) / (2*a)
|
||||
|
||||
print "x1: " print x1 newline
|
||||
print "x2: " print x2 newline
|
||||
Reference in New Issue
Block a user