import java.io.PrintStream; /** * This class performs exaustiv tests on the main class of the Vektoren * project. Call <tt>test_All</tt> to perform all tests. This class is * used only for debugging perposes. I didn't take care about overlong * lines in this modul. */ public class TestVektoren { public static boolean test_All( PrintStream log ) { boolean bOk = true; try { bOk &= test_Value( log ); bOk &= test_Scanner( log ); bOk &= test_Parser( log ); } catch( Exception e ) { log.println( e.getMessage() ); e.printStackTrace( log ); bOk = false; } log.println((bOk ? "[OK]": "[ERR]") + "test_All"); return bOk; } public static boolean test_Value( PrintStream log ) { boolean bOk = true; final double epsilon = 1e-5; try { { Value val = new Value( 1.23456 ); bOk &= Math.abs( val.getX() - 1.23456 ) <= epsilon; bOk &= val.getType() == Value.typeScalar; } { Value val = new Value( 1, 2, 3 ); bOk &= val.getX() == 1; bOk &= val.getY() == 2; bOk &= val.getZ() == 3; bOk &= val.getType() == Value.typeVector; } bOk &= new Value( 1 ).add( new Value( 2 ) ).equals( 3, epsilon ); bOk &= new Value( 1, 2, 3 ).add( new Value( 4, 5, 6 ) ).equals( 5, 7, 9 , epsilon ); bOk &= new Value( 1 ).subtract( new Value( 2 )).equals( -1 , epsilon ); bOk &= new Value( 1, 2, 3).subtract( new Value( -4, -5, -6) ).equals( 5, 7, 9, epsilon ); bOk &= new Value( 1 ).negate().equals( -1, epsilon ); bOk &= new Value( 1, 2, 3 ).negate().equals( -1, -2, -3, epsilon ); bOk &= new Value( 1.5 ).multiply( new Value( 2.3 )).equals( 3.45 , epsilon ); bOk &= new Value( 1.2, 2.3, 4.5 ).multiply( new Value( 2 ) ).equals( 2.4, 4.6, 9.0, epsilon ); bOk &= new Value( 2 ).multiply( new Value( 1.2, 2.3, 4.5 ) ).equals( 2.4, 4.6, 9.0, epsilon ); bOk &= new Value( 1, 2, 3).multiply( new Value( 4, 5, 6 )).equals( -3, 6, -3, epsilon ); bOk &= new Value( 42.45 ).toString().equals("42.450"); bOk &= new Value( 1, 2, 3 ).toString().equals("[ 1.000 , 2.000 , 3.000 ]"); } catch( Exception e ) { bOk = false; } try { // exception expected! new Value( 1 ).add( new Value( 1, 2, 3 ) ); bOk = false; // this statement shouln't be reached } catch( Exception e ) { } try { // exception expected! new Value( 1 ).subtract( new Value( 1, 2, 3 ) ); bOk = false; // this statement shouln't be reached } catch( Exception e ) { } log.println((bOk ? "[OK]": "[ERR]") + "test_Value"); return bOk; } public static boolean test_Scanner_hfn( PrintStream log , String expr , int[] tokens , Value[] values , boolean exceptionExpected ) { boolean bOk = true; boolean bException = false; try { Scanner scanner = new Scanner( expr, true ); int token=Scanner.EOF; int tokenCount=0; int valueCount=0; do { token=scanner.nextToken(); tokenCount++; if ( tokenCount <= tokens.length) { if ( tokens[tokenCount-1] != token ) { // wrong token bOk = false; break; } else { if ( token==Scanner.VECTOR || token==Scanner.SCALAR ) { valueCount++; if ( valueCount <= values.length ) { if ( !scanner.val.equals( values[valueCount-1], 1e-5) ) { bOk = false; break; } } else { // more values found that supplied in values bOk = false; break; } } } } else { // more tokens found that exptected bOk = false; break; } } while ( token != Scanner.EOF ); bOk &= tokenCount == tokens.length && valueCount == values.length; } catch( Exception e ) { log.println("exception: " + e.getMessage() ); bException = true; } bOk &= bException == exceptionExpected; log.println((bOk ? "[OK]": "[ERR]") + "test_Scanner for \"" + expr + "\""); return bOk; } public static boolean test_Scanner( PrintStream log ) { boolean bOk = true; bOk &= test_Scanner_hfn( log, "", new int[] { Scanner.EOF }, new Value[] {}, false ); bOk &= test_Scanner_hfn( log, "(42)", new int[] { Scanner.LPARAN, Scanner.SCALAR, Scanner.RPARAN, Scanner.EOF }, new Value[] { new Value( 42 ) }, false ); bOk &= test_Scanner_hfn( log, "(((42)))", new int[] { Scanner.LPARAN, Scanner.LPARAN, Scanner.LPARAN, Scanner.SCALAR, Scanner.RPARAN, Scanner.RPARAN, Scanner.RPARAN, Scanner.EOF }, new Value[] { new Value( 42 ) }, true ); // nesting level error bOk &= test_Scanner_hfn( log, "(([1,2,3]))", new int[] { Scanner.LPARAN, Scanner.LPARAN, Scanner.VECTOR, Scanner.RPARAN, Scanner.RPARAN, Scanner.EOF }, new Value[] { new Value( 1,2,3 ) }, true ); // nesting level error bOk &= test_Scanner_hfn( log, "(-42)", new int[] { Scanner.LPARAN, Scanner.MINUS, Scanner.SCALAR, Scanner.RPARAN, Scanner.EOF }, new Value[] { new Value( 42 ) }, false ); bOk &= test_Scanner_hfn( log, "(-(-42))", new int[] { Scanner.LPARAN, Scanner.MINUS, Scanner.LPARAN, Scanner.MINUS, Scanner.SCALAR, Scanner.RPARAN, Scanner.RPARAN, Scanner.EOF }, new Value[] { new Value( 42 ) }, false ); bOk &= test_Scanner_hfn( log, "[-1,2,+3.5]", new int[] { Scanner.VECTOR, Scanner.EOF }, new Value[] { new Value( -1,2,3.5 ) }, false ); bOk &= test_Scanner_hfn( log, "[1,2,3", new int[] { Scanner.VECTOR, Scanner.EOF }, new Value[] { new Value( 1,2,3 ) }, true ); bOk &= test_Scanner_hfn( log, "[1,23]", new int[] { Scanner.VECTOR, Scanner.EOF }, new Value[] { new Value( 1,2,3 ) }, true ); bOk &= test_Scanner_hfn( log, "[42]", new int[] { Scanner.VECTOR, Scanner.EOF }, new Value[] { new Value( 1,2,3 ) }, true ); bOk &= test_Scanner_hfn( log, ".", new int[] { Scanner.VECTOR, Scanner.EOF }, new Value[] { }, true ); bOk &= test_Scanner_hfn( log, "a", new int[] { Scanner.VECTOR, Scanner.EOF }, new Value[] { }, true ); bOk &= test_Scanner_hfn( log, "(200)", new int[] { Scanner.LPARAN, Scanner.SCALAR, Scanner.RPARAN, Scanner.EOF }, new Value[] { }, true ); // value out of range bOk &= test_Scanner_hfn( log, "[200,1,0]", new int[] { Scanner.VECTOR, Scanner.EOF }, new Value[] { }, true ); // value out of range bOk &= test_Scanner_hfn( log, "((42))+([1,2,3]*[4,5,6])-[3,2,1]", new int[] { Scanner.LPARAN, Scanner.LPARAN, Scanner.SCALAR, Scanner.RPARAN, Scanner.RPARAN, Scanner.PLUS, Scanner.LPARAN, Scanner.VECTOR, Scanner.MULT, Scanner.VECTOR, Scanner.RPARAN, Scanner.MINUS, Scanner.VECTOR, Scanner.EOF }, new Value[] { new Value( 42 ), new Value( 1, 2, 3 ), new Value(4,5,6), new Value(3,2,1) }, false ); bOk &= test_Scanner_hfn( log, "42", new int[] { Scanner.SCALAR, Scanner.EOF }, new Value[] { new Value( 42 ) }, true ); // scalar must be inbetween () bOk &= test_Scanner_hfn( log, "(42*42)", new int[] { Scanner.LPARAN, Scanner.SCALAR, Scanner.MULT, Scanner.SCALAR, Scanner.RPARAN, Scanner.EOF }, new Value[] { new Value( 42 ), new Value( 42 ) }, true ); // scalar must be inbetween () log.println((bOk ? "[OK]": "[ERR]") + "test_Scanner"); return bOk; } public static boolean test_Parser_hfn( PrintStream log, String expr, double result, boolean exceptionExpected ) { boolean bException=false; boolean bOk = true; try { // not not check with nasty scanner bOk &= new Parser( true ).run(new Scanner( expr, false )).equals( result, 1e-5 ); } catch( Exception e ) { log.println("exception: " + e.getMessage() ); bException=true; } bOk &= bException == exceptionExpected; log.println((bOk ? "[OK]": "[ERR]") + "test_Parser_hfn for \"" + expr + "\""); return bOk; } public static boolean test_Parser_hfn( PrintStream log, String expr, double x, double y, double z, boolean exceptionExpected ) { boolean bException=false; boolean bOk = true; try { // not not check with nasty scanner bOk &= new Parser( true ).run(new Scanner( expr, false )).equals( x, y, z, 1e-5 ); } catch( Exception e ) { log.println("exception: " + e.getMessage() ); bException=true; } bOk &= bException == exceptionExpected; log.println((bOk ? "[OK]": "[ERR]") + "test_Parser_hfn for \"" + expr + "\""); return bOk; } public static boolean test_Parser( PrintStream log ) { boolean bOk = true; bOk &= test_Parser_hfn( log, "42", 42, false ); bOk &= test_Parser_hfn( log, "-42", -42, false ); bOk &= test_Parser_hfn( log, "--42", 42, true ); bOk &= test_Parser_hfn( log, "1--2", 3, false ); bOk &= test_Parser_hfn( log, "1+-2", -1, false ); bOk &= test_Parser_hfn( log, "-1*-1", 1, false ); bOk &= test_Parser_hfn( log, "1*+3+4", 7, false ); bOk &= test_Parser_hfn( log, "-(1)", -1, false ); bOk &= test_Parser_hfn( log, "-(-1)", 1, false ); bOk &= test_Parser_hfn( log, "1+2", 3, false ); bOk &= test_Parser_hfn( log, "1+2+3", 6, false ); bOk &= test_Parser_hfn( log, "1+2*3", 7, false ); bOk &= test_Parser_hfn( log, "1+2*3*4+5", 30, false ); bOk &= test_Parser_hfn( log, "(1+2)*3", 9, false ); bOk &= test_Parser_hfn( log, "[1,2,3]", 1, 2, 3, false ); bOk &= test_Parser_hfn( log, "2*[1,2,3]", 2, 4, 6, false ); bOk &= test_Parser_hfn( log, "(2.3)*[3.2,-12,5]+[0.64,7.6,-1.5]", 8, -20, 10, false ); bOk &= test_Parser_hfn( log, "(1", 1, true ); bOk &= test_Parser_hfn( log, "1+", 1, true ); bOk &= test_Parser_hfn( log, "(1))", 1, true ); bOk &= test_Parser_hfn( log, "1*2*3*4*5*6", 720, true ); // more that 4 operators log.println((bOk ? "[OK]": "[ERR]") + "test_Parser"); return bOk; } }