tags:

views:

228

answers:

9

I am having a difficult time matching up curly brackets in this code. It keeps indicating a "else" without an "if" error but not sure how the syntax should read. If anyone can help it would be most appreciated. Here is the code:

private void compileFactor() {
        boolean its_a_variable = theInfo.isVar();
        if (isIdent(theToken)) {
            String ident = theToken;
            theToken = t.token();       // handles var and const cases!

            IdentInfo theInfo = symTable.lookup(ident);
        }


            boolean its_a_variable = theInfo.isVar();
            int theAddr = theInfo.getAddr(); 
            boolean isGlobal = theInfo.getIsGlobal();
            int constValue = theInfo.getValue();

            if (its_a_variable) {   // pld12: CHANGE THIS!!
                int theAddr = theInfo.getAddr(); 
                boolean isGlobal = theInfo.getIsGlobal();
                if (theAddr == -1) t.error("undeclared identifier used in expr: "+ident);
                if (isGlobal) cs.emit(Machine.LOAD, theAddr);
                else cs.emit(Machine.LOADF, theAddr);
            } else {
                int constValue = theInfo.getValue();
                if (constValue = null) t.error("undeclared identifier used in expr: "+ident);


                else {
                    cs.emitLOADI(theNumber);
                }


            else if (isNumber(theToken)) {
                int theNumber = new Integer(theToken).intValue();
                cs.emitLOADINT(theNumber);
                theToken = t.token();
            }
            else if (equals(theToken, "(")) {  // nothing to do to generate code!
                accept("(");
                compileExpr();
                accept(")");
            }


        }
A: 

I suspect here is your problem.

            if (constValue = null) t.error("undeclared identifier used in expr: "+ident); 


            else { 
                cs.emitLOADI(theNumber); 
            }

EDIT Should this be?

            if (constValue = null) {
                 t.error("undeclared identifier used in expr: "+ident);  
            } else { 
                cs.emitLOADI(theNumber); 
            }
Adam Luchjenbroers
you may have multiple lines between a if-else clause even if the if part is used as an inline statement. Whitespace for the most part does not matter.
Brandon Bodnár
Yeah, but based on indentation, it looked a lot like that if was meant to be joined to that else.
Adam Luchjenbroers
+4  A: 

This else if happens after an else:

        else if (isNumber(theToken)) {
            int theNumber = new Integer(theToken).intValue();
            cs.emitLOADINT(theNumber);
            theToken = t.token();
        }

Edit: fixed and reindented

private void compileFactor() {
    if (isIdent(theToken)) {
        String ident = theToken;
        theToken = t.token();       // handles var and const cases!

        IdentInfo theInfo = symTable.lookup(ident);

        boolean its_a_variable = theInfo.isVar();
        int theAddr = theInfo.getAddr(); 
        boolean isGlobal = theInfo.getIsGlobal();
        int constValue = theInfo.getValue();

        if (its_a_variable) {   // pld12: CHANGE THIS!!
            int theAddr = theInfo.getAddr(); 
            boolean isGlobal = theInfo.getIsGlobal();
            if (theAddr == -1) t.error("undeclared identifier used in expr: "+ident);
            if (isGlobal) cs.emit(Machine.LOAD, theAddr);
            else cs.emit(Machine.LOADF, theAddr);
        } else {
            int constValue = theInfo.getValue();
            if (constValue = null) {
                t.error("undeclared identifier used in expr: "+ident);
            } else {
                cs.emitLOADI(theNumber);
            }
        }
    } else if (isNumber(theToken)) {
        int theNumber = new Integer(theToken).intValue();
        cs.emitLOADINT(theNumber);
        theToken = t.token();
    } else if (equals(theToken, "(")) {  // nothing to do to generate code!
        accept("(");
        compileExpr();
        accept(")");
    }
}
Tordek
That **else if (isNumber(theToken))** might be for **if (isIdent(theToken)) {**, "else if" after "else" does not make sense.
S.Mark
I guessed it didn't make sense; it's missing a closing bracket for the else above it.
Tordek
Yes, Indeed Its need closing brackets there
S.Mark
+1  A: 

Would suggest if you are having problems matching braces, start a new function definition, just start by adding the control flow and branching (ifs, elses,...), and use braces on every if / else if / else block - even the one liners.

When you get that right, add the rest of the function.
When the braces become a no brainer, then start skipping them for one liners.

seanb
...or never start skipping the braces at all. Some people find the code clearer if there is always braces around the code blocks.
Guffa
yup - personally always leave em in, but didn't want to start a holy war :)
seanb
A: 

Few checkpoints

I think you will need to close brackets before isNumber(theToken)

 }} else if (isNumber(theToken)) {

and may be you dont need bracket after this line?

    IdentInfo theInfo = symTable.lookup(ident);
}

May be the whole code is like this?

private void compileFactor() {
    boolean its_a_variable = theInfo.isVar();
    if (isIdent(theToken)) {
     String ident = theToken;
     theToken = t.token();   // handles var and const cases!
     IdentInfo theInfo = symTable.lookup(ident);

     boolean its_a_variable = theInfo.isVar();
     int theAddr = theInfo.getAddr(); 
     boolean isGlobal = theInfo.getIsGlobal();
     int constValue = theInfo.getValue();

     if (its_a_variable) { // pld12: CHANGE THIS!!
       int theAddr = theInfo.getAddr(); 
       boolean isGlobal = theInfo.getIsGlobal();
       if (theAddr == -1) t.error("undeclared identifier used in expr: "+ident);
       if (isGlobal) cs.emit(Machine.LOAD, theAddr);
       else cs.emit(Machine.LOADF, theAddr);
     } else {
       int constValue = theInfo.getValue();
       if (constValue = null) 
       t.error("undeclared identifier used in expr: "+ident);
       else {
         cs.emitLOADI(theNumber);
       }
     }
    } else if (isNumber(theToken)) {
      int theNumber = new Integer(theToken).intValue();
      cs.emitLOADINT(theNumber);
      theToken = t.token();
    } else if (equals(theToken, "(")) {  // nothing to do to generate code!
      accept("(");
      compileExpr();
      accept(")");
    }
}
S.Mark
+4  A: 

I don't want to start a brace placement holy war, but this is why I prefer the "opening brace on the next line" idiom. I can line up the opening and closing brace visually, even if I don't have an IDE to help me.

With that said, an IDE is your best friend here.

I also like the recommendation of immediately adding the opening and closing brace to a block before filling it in.

Eschewing one-line blocks without braces will help. It's not really that much effort to add.

duffymo
+! "I don't want to start a brace placement holy war" oh yes you do...
Simeon Pilgrim
Just stating my reason, that's all.
duffymo
+1  A: 

This is what the structure looks like:

private void compileFactor() {
  if (...) {
    ...
  }
  if (...) {
    ...
    if (...) ...
    if (...) ...
    else ...
  } else {
    if (...) ...
    else {
      ...
*   } else if (...) {
      ...
    } else if (...) {
      ...
    }
  }

Where I have put the * you have an else following an else. Simply adding another bracket before that point doesn't fix it either, as that would put the else after a different else.

So, there is something fundamentally wrong with your conditions, and you pretty much have to rethink it from the start.

Add brackets in all the if statements, so that you are sure that they are really starting and ending where you expect them to.

Guffa
A: 

If you are using Visual Studio, you can use CTRL+ "]" keys to match the braces

ram
A: 

Try commenting code like this:

function blah(){  //start function
  if(...){        //open if 1
   for(...){   //open for

       //do something    

    }//close for  
  } //close if 1  
}//close function

I do it in Flash, although in some langueages it bogs things down.

Good luck!

Moshe
A: 

The posted code has 6 '}' and 7 '{'.

The last '{' statement of the following excerpt is the one that appears to not have a matching '}'

            else cs.emit(Machine.LOADF, theAddr);
    } else {
Phillip Ngan