public class Synchronized2 {
    public static void main (String[] args) throws Exception {
        new Synchronized2().main();
    }
    
    private void main() throws Exception {
        Thread[] T = new Thread[10];
        
        for (int k=0; k < T.length; k++) {
            T[k] = new MyThread();
        }
            
        for (int k=0; k < T.length; k++) {
            T[k].start();
        }
            
        for (int k=0; k < T.length; k++) {
            T[k].join();
        }
            
        System.out.println("Ctr = "+Ctr.value());
        System.out.println("<enter> to exit");
        System.in.read();
    }
    
    Counter Ctr = new Counter();
    
    Object Sync1 = new Object();
    Object Sync2 = new Object();
    
    class MyThread extends Thread {
        public void run() {
            try {
                for (int i=0; i<100; i++) {
                    Ctr.increment();
                    Ctr.decrement();
               }
            } catch (Exception ex) {}
        }
    }
    
    class Counter {
        private int c = 0;

        public void increment() throws Exception {
            synchronized (Sync1) {
                int r = c;
                r += 1;
                Thread.yield();  
                //Thread.sleep((int) (2*Math.random()));
                c = r;
            }
        }

        public void decrement() throws Exception {
            synchronized (Sync1) {
                int r = c;
                r -= 1;
                Thread.yield();  
                //Thread.sleep((int) (2*Math.random()));
                c = r;
            }
        }

        public int value() {
            synchronized (Sync1) {
                return c;
            }
        }

}

}
