java/ch/wlkl/javaExamples/Java.java

/*
 * Expr.java
 *
 * Created on 16. Dezember 2003, 21:23
 */

/**
 *
 * @author  walter
 */
package ch.wlkl.javaExamples;

import static ch.wlkl.env.Env.ind;
import static ch.wlkl.env.Env.out;
import static ch.wlkl.env.Env.outPa;
import java.lang.reflect.*;
import java.io.*;
import java.util.*;
import java.util.regex.*;
import java.text.*;
import static ch.wlkl.env.Env.out;
import static ch.wlkl.env.Env.outPa;

/**
 * javadoc -source 1.4 -d doc *.java Java contains basic language examples
 (expressionss, io, reflection etc. furthermore the invokemethods is used by
 all Java... class to invoke methods dynamically
 <p>
 * to generate the docu use: javadoc -source 1.4 -d doc *.java
 */
public class Java implements Serializable {
    String args[];

    int lastArg;

    public Java() {
        this(new String[0], new String[0]);
    }

    public Java(String aArgs[], String defArgs[]) {
        if (aArgs.length > 0)
            args = aArgs;
        else {
            args = defArgs;
            System.out.println("calling default method " + toString(defArgs));
        }
        lastArg = -1;
    }

    /**
     * array examples: initialisation and access
     */
    public void array() {
        String sArr[][] = {{"00", "01", "02"}, {"10", "11"}, {"20"}};
        sArr = new String [][] {{"a00", "b01", "c02"}, {"10", "11"}, {"20"}};
        int iArr[][][] = new int[3][4][5];
        int i, j;
        out("iArr.length = " + iArr.length + " ==> " + array2String(iArr));
        out("iArr[1].length = " + iArr[1].length + " ==> " + array2String(iArr[1]));
        out("iArr[1][2].length = " + iArr[1][2].length + " ==> " + array2String(iArr[1][2]));
        for (i=0; i< iArr.length; i++)
            out("  iArr[" + i +"] length=" + iArr[i].length + " ==> " + array2String(iArr[i]));
        out("sArr.length = " + sArr.length);
        for (i = 0; i < sArr.length; i++) {
            outPa("sArr[" + i + "].length = " + sArr[i].length
                    + " ==> " + array2String(sArr[i]) + ' ');
        }
        Object[] aObj = {"0: null", 1, 2.0f,
            new String[]{"30", "31"}, null,
            Arrays.asList(new String[]{"50_", "51_"}), "sechs:6"};
        out("aObj class " + aObj.getClass() + ", aObj " + aObj);
        List lObj = Arrays.asList(aObj);
        out("lObj class " + lObj.getClass() + ", lObj " + lObj);
    }
    
    /**
     * display the elements of an array as a String surrounded by {}
     * @param <T> componentType of aa
     * @param a the array to show
     * @return a String containing {a[0], a[1], ... }
     */
    public static <T> String array2String(T[] a) {
        StringBuilder b = new StringBuilder("{");
        if (a.length > 0) {
            b.append(a[0]);
            for (int i=1; i < a.length; i++) {
                b.append(", ").append(a[i]);
            }            
        }
        return b.append('}').toString();
    }

    /**
     * similar to the generic method but for a int[] which does not work for arrays of primitive types
     * @param a
     * @return
     */
    public static  String array2String(int[] a) {
        StringBuilder b = new StringBuilder("{");
        if (a.length > 0) {
            b.append(a[0]);
            for (int i=1; i < a.length; i++) {
                b.append(", ").append(a[i]);
            }            
        }
        return b.append('}').toString();
    }

    /**
     * output info of a class
     * @param cl the class to show
     */
    static void outClass(Class cl) {
        out("class=" + cl + " simpleName="+ cl.getSimpleName()
           + " package=" + (cl.getPackage() == null ? "null" : cl.getPackage().getName())
           + " primitive=" + cl.isPrimitive() 
           + ", super=" + (cl.getSuperclass() == null ? "null" : cl.getSuperclass().getName())
           + ", array=" + cl.isArray());
        if (null != cl.getComponentType()) {
            ind(+1).outPa("component: ");
            outClass(cl.getComponentType());
            ind(-1);
        }
    }
    
    /**
     * output an object, size of array if it is an array and outClass
     */
    static void outObj(Object o) {
        outPa("object=" + o + " ");
        if (o instanceof Object[]) {
            outPa("Obj[].length=" + ((Object[])o).length + " ");
        }
        if (o instanceof int[]) {
            outPa("int[].length=" + ((int[])o).length + " ");
        }
        outClass(o.getClass());
    }
    
    /**
     *  show different class and arrayclasses
     *  Array.newInstance to create arrays
     */
    public void arrayNew() {
        outClass(Integer.class);
        outClass(Integer.TYPE);
        outClass(String[].class);
        outClass(boolean[].class);
        outClass(double[][][].class);
        outClass(Array.newInstance(getClass(), 3).getClass());
        outClass(Array.newInstance(int[].class, 3).getClass());
        try {
         outObj(Array.newInstance(int[][].class, 5));
         outObj(Array.newInstance(int.class, 7));
         outObj(Array.newInstance(long.class, 7));
         outObj(Array.newInstance(short.class, 7));
        } catch (Throwable e) {
            out("catch " + e);
        }
    }

   /**
     * get the next argument string
     */
    public static String toString(Object[] arr) {
        StringBuffer buf = new StringBuffer("{");
        for (int i = 0; i < arr.length; i++) {
            if (buf.length() > 1) {
                buf.append(", ");
            }
            buf.append(arr[i]);
        }
        buf.append('}');
        return buf.toString();
    }

    public String nextString() {
        if (++lastArg >= args.length) {
            System.out.println("no args[" + lastArg + "] after "
                    + args[lastArg - 1]);
        }
        /**
         * and now return it
         */
        return args[lastArg];
    }

    int nextInt() {
        return Integer.parseInt(nextString());
    }
        
        

    /**
     * invoke the method name for Object obj if the method need arguments, they
     * are take from (the next) args
     */
    public void invokeMethod(Object obj, String name) {
        Method all[] = obj.getClass().getDeclaredMethods();
        Method met;
        for (int i = 0;; i++) {
            if (i >= all.length) {
                System.out.println(name + "(...) not found in "
                        + obj.getClass());
                System.out.println(all.length + " methods available:");
                for (int ix = 0; ix < all.length; ix++)
                    System.out.println(all[ix]);
                return;
            }
            if (name.equals(all[i].getName())) {
                met = all[i];
                break;
            }
        }
        Class clArgs[] = met.getParameterTypes();
        Object args[] = new Object[clArgs.length];
        String txt = met.getName();
        try {
            for (int i = 0; i < clArgs.length; i++) {
                if (clArgs[i] == String.class)
                    args[i] = nextString();
                else if (clArgs[i] == Integer.class
                        || clArgs[i] == Integer.TYPE)
                    args[i] = new Integer(nextString());
                else
                    throw new Throwable("argument class " + clArgs[i]
                            + " not supported");
            }
            txt += toString(args);
            System.out.println("invoking " + txt);
            Object res = met.invoke(obj, args);
            System.out.println(txt + " returns " + res);
        } catch (Throwable ex) {
            System.out.println("failed   " + txt + " in " + obj.getClass()
                    + ": " + ex + ", reason: " + ex.getCause());
            ex.printStackTrace(System.out);
        }
    }

    /**
     * invoke the methods specified in args. If a method needs parameters, they
     * are also taken from args
     */
    public void invokeMethods(Object obj) {
        while (args.length > lastArg + 1)
            invokeMethod(obj, nextString());
    }

    public void objInfo(Object obj) {
        System.out.println("classInfo for obj " + obj);
        if (obj == null)
            System.out.println("obj is null");
        else
            classInfo(obj.getClass());
    }

    public void classInfo(Class c) {
        for (int cx = 0; c != null && cx < 10; cx++) {
            System.out.println((cx == 0 ? "class " : "superClass ") + c
                    + " =========");
            Method[] meths = c.getDeclaredMethods();
            for (int ix = 0; ix < meths.length; ix++)
                System.out.println("meth " + ix + ": " + meths[ix]);
            c = c.getSuperclass();
        }
    }

    void reflect() {
        objInfo(this);
        objInfo(null);
        objInfo(this.getClass());
    }

    public static StackTraceElement frame(int ix) {
        try {
            throw new Exception();
        } catch (Exception e) {
            StackTraceElement[] st = e.getStackTrace();
            //        for (int i = 0; i < st.length; i++)
            //          System.out.println(
            //            "stack " + i + ": " + st[i].getClassName() + "." +
            // st[i].getMethodName());
            return st.length >= ix ? st[ix] : null;
        }
    }

    public static StackTraceElement thisFrame() {
        return frame(2);
    }

    public static String packagePrefix() {
        String na = frame(2).getClassName();
        int ix = na.lastIndexOf('.');
        return ix < 0 ? "" : na.substring(0, ix).replaceAll("\\.",
                File.separator)
                + File.separator;
    }

    public static Method thisMethod() {
        try {
            StackTraceElement fr = frame(2);
            Class cl = Class.forName(fr.getClassName());
            InputStream src = cl.getClassLoader().getResourceAsStream(
                    fr.getFileName());
            BufferedReader bs = new BufferedReader(new InputStreamReader(src));
            int i = 0;
            String li;
            while (null != (li = bs.readLine()))
                System.out.println("src " + ++i + ": " + li);
            return null;
            //        Method me [] = cl.getDeclaredMethods();
            //        me[0].
        } catch (Exception e) {
            return null;
        }
    }

    static void test1(String arg) {
        System.out.println("test1(String " + arg + ")");
        System.out.println("method " + thisFrame());
        System.out.println("packagePrefix " + packagePrefix());
    }

    void test1(int arg) {
        System.out.println("test1(int " + arg + ")");
    }

    /**
     * @deprecated as of today
     */
    void test1(Integer arg) {
        System.out.println("test1(Integer " + arg + ")");
    }

    void test1(float arg) {
        System.out.println("test1(float " + arg + ")");
    }

    void overload() {
        System.out.println("overload test1 eins, 2, new Integer(3), 4.56f");
        test1("eins");
        test1(2);
        test1(new Integer(3));
        test1(4.56f);
        test1((byte) 'a');
        test1((char) 'b');
    }

    void limits() {
        System.out.println("Byte      max " + Byte.MAX_VALUE + " min "
                + Byte.MIN_VALUE);
        System.out.println("Character max " + (int) Character.MAX_VALUE
                + " min " + (int) Character.MIN_VALUE);
        System.out.println("Short     max " + Short.MAX_VALUE + " min "
                + Short.MIN_VALUE);
        System.out.println("Integer   max " + Integer.MAX_VALUE + " min "
                + Integer.MIN_VALUE);
        System.out.println("Long      max " + Long.MAX_VALUE + " min "
                + Long.MIN_VALUE);
        System.out.println("Float     max " + Float.MAX_VALUE + " min "
                + Float.MIN_VALUE);
        System.out.println("Double    max " + Double.MAX_VALUE + " min "
                + Double.MIN_VALUE);
    }

    final File myDir = new File("d:\\java");

    String mark = "ExIni";

    void appL(StringBuffer sb, String sv, int len) {
        for (int r = len > sv.length() ? len - sv.length() : 1; r > 0; r--)
            sb.append(' ');
        sb.append(sv);
    }

    void appR(StringBuffer sb, String sv, int len) {
        sb.append(sv);
        for (int r = len > sv.length() ? len - sv.length() : 1; r > 0; r--)
            sb.append(' ');
    }

    void sh(String expr, String res) {
        StringBuffer b = new StringBuffer(100);
        appR(b, expr, 40);
        b.append(" = ");
        b.append(res);
        System.out.println(b);
    }

    void sh(String expr, int res) {
        StringBuffer b = new StringBuffer(100);
        appR(b, String.valueOf(res), 10);
        b.append("0x");
        b.append(Integer.toHexString(res));
        sh(expr, b.toString());
    }

    void sh(String expr, boolean res) {
        sh(expr, String.valueOf(res));
    }

    void intExpr2(int le, int ri) {
        sh("******** le", le);
        sh("******** ri", ri);
        sh("~" + ri, ~ri);
        sh(le + " ^ " + ri, le ^ ri);
        sh(le + " & " + ri, le & ri);
        sh(le + " | " + ri, le | ri);
        sh(le + " << " + ri, le << ri);
        sh(le + " >> " + ri, le >> ri);
        sh(le + " >>> " + ri, le >>> ri);

    };

    void intExpr() {
        sh("\\u004f", '\u004f');
        sh("0x4748494a", 0x4748494a);
        sh("0xc748494a", 0xc748494a);
        sh("0x12345678", 0x12345678);
        sh("0xedcba987", 0xedcba987);
        sh("0x80000000", 0x80000000);
        sh("-0x80000000", -0x80000000);
        sh("0x12345678", 0x12345678);
        sh("- 0xf1", -0xf1);
        sh("0xf1 >> 4", 0xf1 >> 4);
        sh("0xf1 >>> 4", 0xf1 >>> 4);
        sh("(byte)0xf1", (byte) 0xf1);
        sh("(byte)0xf1 >> 4", (byte) 0xf1 >> 4);
        sh("(byte)0xf1 >>> 4", (byte) 0xf1 >>> 4);
        sh("rint(0.5)", (int) Math.rint(0.5));

        intExpr2(5, 20);
        intExpr2(0, 20);
        intExpr2(5, 69);
        intExpr2(-7, 4);
    }

    long cnt;

    java.math.BigInteger fibonacciRec(long arg) {
        if (arg < 2)
            return java.math.BigInteger.ONE;
        cnt++;
        return fibonacciRec(arg - 1).add(fibonacciRec(arg - 2));
    }

    java.math.BigInteger fibonacciIt(long arg) {
        java.math.BigInteger n, a = java.math.BigInteger.ONE, p = a;
        while (--arg > 0) {
            n = p.add(a);
            p = a;
            a = n;
            cnt++;
        }
        return a;
    }

    void fibonacci(int it) {
        for (long i = 0;; i = i < 8 ? i + 1 : i * 2) {
            long strt = System.currentTimeMillis();
            cnt = 0;
            java.math.BigInteger p = (it != 0 ? fibonacciIt(i)
                    : fibonacciRec(i));
            System.out.println("fibonacci(" + i + ") " + p.bitLength()
                    + " bits" + " with " + cnt + " adds in "
                    + ((float) (System.currentTimeMillis() - strt)) / 1000
                    + " secs = " + p);
        }
    }

    java.math.BigInteger fakIt(java.math.BigInteger arg) {
        java.math.BigInteger p;
        for (p = arg; (arg = arg.subtract(java.math.BigInteger.ONE))
                .compareTo(java.math.BigInteger.ONE) > 0; p = p.multiply(arg))
            ;
        return p;
    }

    java.math.BigInteger fakRec(java.math.BigInteger arg) {
        return arg.compareTo(java.math.BigInteger.ONE) <= 0 ? java.math.BigInteger.ONE
                : fakRec(arg.subtract(java.math.BigInteger.ONE)).multiply(arg);
    }

    void fak(int it) {
        for (long i = 0;; i = i < 8 ? i + 1 : i * 2) {
            long strt = System.currentTimeMillis();
            java.math.BigInteger f = new java.math.BigInteger(String.valueOf(i));
            f = (it != 0) ? fakIt(f) : fakRec(f);
            System.out.println("fak(" + i + ") = " + f.bitLength()
                    + " bits, in = "
                    + ((float) (System.currentTimeMillis() - strt)) / 1000
                    + " secs, = " + f);
        }
    }

    void stringExpr2(String le, String ri) {
        sh(le + " .equals(" + ri + ")", String.valueOf(le.equals(ri)));
        sh(le + " .compareTo(" + ri + ")", new Integer(le.compareTo(ri))
                .toString());
        sh(le + " .startsWith(" + ri + ")", String.valueOf(le.startsWith(ri)));
        sh(le + " .indexOf(" + ri + ")", String.valueOf(le.indexOf(ri)));
        sh(ri + " .replace('c', 'X')", ri.replace('c', 'X'));
        sh(ri + " .substring(1, 3)", String.valueOf(ri.substring(1, 3)));
        sh(ri + " .charAt(1)", String.valueOf(ri.charAt(1)));
        sh(ri + " .toCharArray()", String.valueOf(ri.toCharArray()));
        sh("new StringBuffer(" + le + ").append(" + ri + ")...(1/3)..",
                new StringBuffer(le).append(ri).append(1.0 / 3).toString());
        sh("new StringBuffer(" + le + ").insert(3, " + ri + ").(8,1/3)..",
                new StringBuffer(le).insert(3, ri).insert(7, 1.0 / 3)
                        .toString());
    }

    void stringExpr() {
        stringExpr2("ach so", "ach so");
        stringExpr2("ach so", "ach nein");
        stringExpr2("ach so", "ach");
        stringExpr2("ach so", " so");
        String txt = "auch das ist ein Satz, oder nicht?";
        String sPat = "\\p{L}+";
        Pattern pat = Pattern.compile(sPat);
        System.out.println("compiled " + sPat + " to " + pat + " scanning "
                + txt);
        for (Matcher mat = pat.matcher(txt); mat.find();)
            System.out.println("found group " + mat.group() + " start "
                    + mat.start() + " end " + mat.end());
        pat = Pattern.compile(sPat = "(\\w*)([ai])(\\w*)");
        System.out.println("compiled " + sPat + " to " + pat + " scanning "
                + txt);
        for (Matcher mat = pat.matcher(txt); mat.find();)
            System.out.println("found group " + mat.group() + " 1: "
                    + mat.group(1) + " 2: " + mat.group(2));
        Date da = new Date();
        Calendar cal = Calendar.getInstance();
        cal.setTime(da);
        System.out.println("date " + da + " cal.get(Calendar.YEAR) "
                + cal.get(Calendar.YEAR));
        System.out.println("SimpleDateFormat yyyy.MM.dd HH:mm:ss.SSS "
                + new SimpleDateFormat("yyyy.MM.dd HH:mm:ss.SSS").format(da));
    }

    void divExpr() {
        sh("\"a\" instanceof String", "a" instanceof String);
        sh("String.class.isInstance(\"a\")", String.class.isInstance("a"));
        // sh("String.class.isInstance(\"a\")", String.class.isInstance('a'));
        // syntax !
        // sh("'a' instanceof String", (boolean) (23 instanceof int)); // syntax
        // !
    }

    void charset() {
        char x = 0;
        for (x = 0; x < 128; x++)
            if (Character.isDefined(x))
                System.out.println("char " + x + " whSP "
                        + Character.isWhitespace(x) + " spac "
                        + Character.isSpaceChar(x) + " uniI "
                        + Character.isUnicodeIdentifierPart(x) + " int "
                        + (int) x);
    }

    void inputStream() throws java.io.IOException {
        StringBuffer cont = new StringBuffer();
        int cc, cnts[] = new int[999];
        while ((cc = System.in.read()) != -1) {
            cont.append((char) cc);
            cnts[cc]++;
            System.out.println("read char " + cc + " = " + (char) cc);
        }
        System.out.println("got input: " + cont);
        for (int i = 0; i < cnts.length; i++)
            if (cnts[i] != 0)
                System.out.println(i + " '" + (char) i + "' #" + cnts[i]);
    }

    void doThrow() {
        int r;
        for (int i = -1; i <= 3; i++) {
            try {
                System.out.println("trying " + i);
                switch (i) {
                case 0:
                    r = 13 / i;
                    break;
                case 1:
                    r = (new int[0])[i];
                    break;
                case 2:
                    throw new Throwable("throw zwei");
                }
            } catch (Throwable th) {
                System.out.println("catch " + th);
                th.printStackTrace(System.out);
            } finally {
                System.out.println("finally " + i);
            }
            ;
        }
        Throwable th = new Throwable("eins");
        System.out.println("new Throwable " + th);
        th.printStackTrace(System.out);
        th.fillInStackTrace();
        System.out.println("after fillInStackTrace " + th);
        // System.out.flush();
        th.printStackTrace(System.out);
        // System.err.flush();
        System.out.println("end of doThrow");
    }

    void bufferedReader() throws java.io.IOException {
        StringBuffer cont = new StringBuffer();
        int cc, cnts[] = new int[999];
        String txt;
        BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
        while ((txt = in.readLine()) != null) {
            System.out.println("readLine: " + txt);
            for (int i = 0; i < txt.length(); i++)
                cnts[txt.charAt(i)]++;
            cont.append(txt);
        }
        System.out.println("got input: " + cont);
        for (int i = 0; i < cnts.length; i++)
            if (cnts[i] != 0)
                System.out.println(i + " '" + (char) i + "' #" + cnts[i]);
    }

    void file() throws Throwable {
        File r1[] = File.listRoots();
        File roots[] = new File[r1.length + 1];
        for (int i = 0; i < r1.length; i++)
            roots[i] = r1[i];
        roots[roots.length - 1] = myDir;
        System.out.println(roots.length + " roots: " + roots);
        for (int i = 0; i < roots.length; i++) {
            StringBuffer t = new StringBuffer();
            File lst[] = roots[i].listFiles();
            if (lst != null)
                for (int j = 0; j < lst.length; j++) {
                    t.append(lst[j]);
                    if (lst[j].isFile())
                        try {
                            t.append(" #"
                                    + new FileInputStream(lst[j]).available());
                        } catch (Throwable ex) {
                            t.append(" !" + ex + "!");
                        }
                    t.append(", ");
                }
            System.out.println(roots[i] + "(" + lst + ") contains " + t);
        }
        File src = new File(myDir, getClass().getName() + ".java");
        // FileInputStream fi = new FileInputStream(src);
        BufferedReader br = new BufferedReader(new FileReader(src));
        System.out.println("reader " + br + ", file " + src);
        String t;
        for (int i = 0; i < 10 && (t = br.readLine()) != null; i++) {
            String q = "";
            String s[] = t.trim().split("\\s+");
            for (int j = 0; j < s.length; j++)
                q += s[j] + ", ";
            System.out.println(i + " split " + s.length + ": " + q + " from "
                    + t);
        }

    }

    static int graf2Cnt = 0;

    class Graf2 implements Serializable {
        String txt;

        int inst;

        Graf2 le, ri;

        protected Graf2() {
            inst = graf2Cnt++;
        }

        public String toString() {
            return "Graf2(" + inst + ":" + txt + ")";
        }

        Graf2(int pr, int limit) {
            this();
            txt = String.valueOf(pr);
            if (limit < 1)
                le = ri = null;
            else {
                le = new Graf2(10 * pr, limit - 1);
                ri = new Graf2(10 * pr + 3, limit - 1);
            }
        }

        void list() {
            System.out.println("list for Ex.mark " + mark + ", graf2Cnt "
                    + graf2Cnt);
            list(new HashSet());
        }

        void list(Set done) {
            if ((le == null && ri == null) || done.contains(this))
                return;
            done.add(this);
            System.out.println(this + ": le " + le + ", ri " + ri);
            if (le != null)
                le.list(done);
            if (ri != null)
                ri.list(done);
        }
    }

    void objectStream() throws Throwable {

        Graf2 g = new Graf2(1, 3);
        g.ri.ri.le = g;
        g.ri.ri.ri = g.ri.ri;
        g.list();
        final File myFile = new File(myDir, "os.dat");
        ObjectOutputStream oo = new ObjectOutputStream(new FileOutputStream(
                myFile));
        oo.writeObject(g);
        oo.close();
        g.txt = g.le.txt = g.ri.txt = g.le.le.txt = g.ri.ri.txt = g.ri.ri.le.txt = g.ri.ri.ri.txt = g.ri.ri.txt = "old";
        mark = "ExMarkOld";
        ObjectInputStream oi = new ObjectInputStream(
                new FileInputStream(myFile));
        Object ob = oi.readObject();
        System.out.println("read obj: " + ob.getClass() + ": " + ob);
        ((Graf2) ob).list();
        System.out.println("old obj: ");
        g.list();
    }

    void xmlEncoder() throws Throwable {

        mark = "ExMarkOne";
        Graf2 g = new Graf2(1, 3);
        g.ri.ri.le = g;
        g.ri.ri.ri = g.ri.ri;
        g.list();
        File myFile = new File(myDir, "os.xml");
        java.beans.XMLEncoder oo = new java.beans.XMLEncoder(
                new FileOutputStream(myFile));
        oo.writeObject("String eins");
        oo.writeObject(new Float(1.1));
        oo.writeObject(g);
        oo.close();
        g.txt = g.le.txt = g.ri.txt = g.le.le.txt = g.ri.ri.txt = g.ri.ri.le.txt = g.ri.ri.ri.txt = g.ri.ri.txt = "old";
        mark = "ExMarkTwo";
        java.beans.XMLDecoder oi = new java.beans.XMLDecoder(
                new FileInputStream(myFile));
        Object ob;
        while ((ob = oi.readObject()) != null) {
            System.out.println("read obj: " + ob.getClass() + ": " + ob);
        }
        /*
         * ((Graf2) ob).list(); System.out.println("old obj: "); g.list();
         */
    }

    void assertion() {
        System.out.println("assert need compile with source1.4 and run with ea (enable assert)");
        System.out.println("before assert true");
        assert true : "assert true";
        System.out.println("before assert false");
        assert false : "assert false";
        System.out.println("after assert false");
    }

    void thread() {
        Thread it = Thread.currentThread();
        System.out.println("I thread " + it);
        ThreadGroup tg = it.getThreadGroup();
        for (;;) {
            System.out.println("ThreadGroup" + tg);
            if (tg.getParent() == null) {
                break;
            }
            tg = tg.getParent();
        }

        new Thread("threadAAA") {
            public void run() {
                System.currentTimeMillis();
                for (int i = 0; i < 5; i++)
                    try {
                        System.out.println("thread A " + i);
                        sleep(1500);
                    } catch (Throwable ex) {
                        System.out.println("thread A catch " + ex);
                    }
            }

        }.start();
        new Thread("threadBBB") {
            public void run() {
                for (int i = 0; i < 8; i++)
                    try {
                        System.out.println("thread BBB " + i);
                        sleep(940);
                    } catch (Throwable ex) {
                        System.out.println("thread B catch " + ex);
                    }
            }
        }.start();
        Thread all[] = new Thread[tg.activeCount() + 10];
        int cnt = tg.enumerate(all);
        for (int i = 0; i < cnt; i++)
            System.out.println(i + ": " + all[i]);
    }

    void threadInter() throws InterruptedException {
        Thread th = new Thread() {
            public void run() {
                while (true) {
                    try {
                        sleep(1000000);
                    } catch (InterruptedException ex) {
                        System.out.println("thread sleep interrupted by " + ex
                                + ", cause " + ex.getCause());
                    } catch (ThreadDeath ex) {
                        System.out.println("threadDeath (by " + ex + ", cause "
                                + ex.getCause());
                    }
                }
            }
        };
        th.start();
        for (int i = 3; i >= 0; i--) {
            Thread.sleep(1000);
            th.interrupt();
            Thread.sleep(1000);
            th.stop();
        }
    }

    void threadSync() throws InterruptedException {
        final StringBuffer s = new StringBuffer("ini");
        Thread thr[] = new Thread[40];
        for (int i = 0; i < 3; i++) {
            final int fi = i;
            thr[fi] = new Thread() {
                public void run() {
                    for (int k = 0; k < 3; k++)
                        synchronized (s) {
                            System.out.println("begin " + fi + ", s " + s);
                            s.append(", lock_" + fi);
                            try {
                                sleep(1000);
                            } catch (Exception ex) {
                                ;
                            }
                            ;
                            s.append("_" + k + "_free");
                            System.out.println("end " + fi + ", s " + s);
                        }
                }
            };
            s.notifyAll();
            thr[fi].start();
        }
        System.out.println("started 3 threads");
        for (int i = 0; thr[i] != null; i++) {
            thr[i].join();
            System.out.println("join'd thr[" + i + "]");
        }
    }

    void timer(int cnt) throws InterruptedException {
        Timer[] ti = new Timer[cnt];
        final SimpleDateFormat df = new SimpleDateFormat("hh:mm:ss.SSS");
        for (int i = 0; i < cnt; i++) {
            final int fi = i;
            final int del = i * 1000;
            final int per = i < 10 ? (10 - i) * 500 : 2000;
            TimerTask tt = new TimerTask() {
                int nr = 0;

                public void run() {
                    try {
                        Thread.sleep(500);
                    } catch (InterruptedException ex) {
                    }
                    ;
                    System.out.println("TimerTask " + fi + " del " + del
                            + " per " + per + " nr " + ++nr + " at "
                            + df.format(new Date()) + ", scheduled "
                            + df.format(new Date(scheduledExecutionTime()))
                            + ", thread " + Thread.currentThread());
                }
            };

            (ti[i] = new Timer()).schedule(tt, del, per);
        }
        System.out.println("scheduled " + cnt + " timers, at "
                + df.format(new Date()) + ", thread " + Thread.currentThread());
        Thread.sleep(30 * 1000);
        for (int i = 0; i < cnt; i++)
            ti[i].cancel();
        System.out.println("ti[0.." + (cnt - 1) + "].cancel()");
    }

    void properties() {
        System.getProperties().list(System.out);
        System.out.println("user.dir => " + System.getProperty("user.dir"));
        System.out.println("user.Dir => " + System.getProperty("user.Dir"));
        System.out.println("sun.boot.class.path => "
                + System.getProperty("sun.boot.class.path"));
        System.out.println("java.class.path => "
                + System.getProperty("java.class.path"));
        // wak? Object x = new sun.tools.javac.Main(System.out, "sdf");
    }

    void exec() throws IOException {
        String cmd = "cmd.exe /C echo eins zwei dri && echo path is: %path% && cd && dir";
        System.out
                .println("exec cmd (cmd.exe /C to invoke cmd only for given arguments): "
                        + cmd);
        Process p = Runtime.getRuntime().exec(cmd);
        BufferedReader pIn = new BufferedReader(new InputStreamReader(p
                .getInputStream()));
        String ln;
        while ((ln = pIn.readLine()) != null)
            System.out.println("exec(dir) inputStream: " + ln);
    }

    void token() throws FileNotFoundException, IOException {
        boolean noEx = false;
        String sent = "und wie, geht     es +-/* dir?";
        System.out.println("StringTokenizer for " + sent);
        for (StringTokenizer tk = new StringTokenizer(sent); tk.hasMoreTokens()
                || noEx;)
            System.out.println("token '" + tk.nextToken() + "'");
        File src = new File(myDir, "Ex.java");
        StreamTokenizer st = new StreamTokenizer(new FileReader(src));
        if (true) {
            st.slashStarComments(true);
            System.out.println("StreamTokenizer for " + src + " = " + st
                    + ", with slashStarComments(true)");
        } else {
            st.slashStarComments(false);
            st.ordinaryChar('/');
            System.out.println("StreamTokenizer for " + src + " = " + st
                    + ", with slashStarComments(false) and ordinaryChar('/')");
        }
        for (int i = 0; i < 30; i++)
            System.out.println(i + " nextToken " + st.nextToken() + ", sval "
                    + st.sval + ", nval " + st.nval + ", toString "
                    + st.toString());
    }

    public String thisSuperS = "{Ex-" + this + "}"; // field lookup in NEVER
                                                    // virtual!
    class ExS1 extends Java {

        public String thisSuperS = "{S1-" + this + "}";

        public void thisSuper(String txt) {
            txt += " -> S1";
            thisSuper2(txt + ".this");
            super.thisSuper2(txt + ".supr");
            if (txt.length() < 50) {
                thisSuper(txt + ".this");
                super.thisSuper(txt + ".supr");
            }
        }

        public void thisSuper2(String txt) {
            System.out.println(txt + " S1 2 String " + thisSuperS + " sup "
                    + super.thisSuperS);
        }
    }

    class ExS2 extends ExS1 {

        public String thisSuperS = "{S2-" + this + "}";

        public void thisSuper(String txt) {
            txt += " -> S2";
            this.thisSuper2(txt + ".this");
            super.thisSuper2(txt + ".supr");
            if (txt.length() < 50) {
                this.thisSuper(txt + ".this");
                super.thisSuper(txt + ".supr");
            }
        }

        public void thisSuper2(String txt) {
            System.out.println(txt + " S2 2 String " + thisSuperS + " sup "
                    + super.thisSuperS);
        }
    }

    public void thisSuper(String txt) {
        txt += " -> Ex";
        this.thisSuper2(txt + ".this");
        if (txt.length() < 50) {
            this.thisSuper(txt + ".this");
        }
    }

    public void thisSuper2(String txt) {
        System.out.println(txt + " Ex 2 String " + thisSuperS);
    }

    public Java n(String n) {
        out("--- " + n + " ----------");
        return this;
    }

    public void all() {
        n("array()").array();
        n("arrayNew()").arrayNew();
    }

    public static void main(String[] args) {
        new Java().all();
        /* ??????????????????
        System.out.println("start of main of Ex");
            if (false) {
                int sum = 0, current;
                for (current = 1; current <= 10; current++) {
                    sum += current;
                }
                System.out.println("Sum [1.." + --current + "] = " + sum);
            } else {
                // Java inst = new Java( args, new String [] { "overload", "reflect",
                // "doThrow", "intExpr","stringExpr", "stringExpr2", "a-", "b-"} );
                // Java inst = new Java( args, new String [] { "test1", "arg",
                // "packagePrefix", "stringExpr"} );
                Java inst = new Java(args, new String[]{"thisSuper", ":"});
                inst.invokeMethods(new ExS2());
            }
????????????????? */
    }

}