September 28, 2011

Currently reading

Picked up this set while browsing B&N. Pulpy, fun story that deals with a post-nuclear terrorist world and is centered around one of the few untouched cities--London--which is now a megalopolis called The Metrozone. The terrorists who took down the world were non-specific religious armogeddonists. When the US is mentioned it's described as a xenophobic and thinly veiled theocracy, so nothing much has changed. The main character is a Russian physicist/badass whose exploits are far less believable than even pulp should allow. Still, enjoyable enough to keep me through the set.

Continue reading "Currently reading"
posted by sstrader at 2:01 PM in Current Interests , Language & Literature | permalink

September 21, 2011

September 4, 2011

The labeled break in Java

Trying to optimize the Android app I'm working on and found this Java feature that I'm sure I knew at one point but ignored as useless. My mistake.

The code I'm working on is in the script parser. The parser has one class method per grammar rule (e.g. parser.processStatement() or parser.processExpression()) following general top-down parsing practice. Within each method/rule, the parser can fail on a token without being certain that the token won't satisfy a subsequent rule. For example: if processStatementLoop() is called before processStatementConditional() and an "if" is the first token encountered in the script, the token stack (and possibly other internal structures) needs to rewind after processStatementLoop() fails on "if". The parser needs to know that the grammar has not yet accepted the "if" as valid. So, a rule may fail on a valid script.

When the grammar was small, I started with various conditionals peppered through each method, unwinding the relevant structures if the rule failed. I changed the conditionals to exceptions because it was easier to manage multiple failures within a single rule. However, the exceptions could be thrown either because of an error in the script or because of simple backtracking in the grammar. The latter isn't a true exception, and so this could be considered misuse of the exception construct.

	private boolean processStatementLoop() {
		transaction.begin();
		try {
			if (!processToken(TOKEN_FOR, true)) {
				throw new ScriptException(tokenizer);
			}

			// ...

		} catch (ScriptException e) {
			transaction.rollback();
			return false;
		}
		transaction.end();
		return true;
	}

And so I pondered and searched on a substitute for the exception in this instance. I'm not sure how I found it, but the Java doc article Branching Statements described the mysterious labeled break. Using this, you can break out of a block a la the "beloved" retro GOTO statement:

	private boolean processStatementLoop() {
		transaction.begin();
		Transaction: {
			if (!processToken(TOKEN_FOR, true)) {
				break Transaction;
			}

			// ...

			transaction.end();
			return true;
		}
		transaction.rollback();
		return false;
	}

This (should) avoid the cost of exception construction and stack unwinding, but more importantly it more closely maps the code's intent.

posted by sstrader at 11:27 AM in Programming | permalink