Java ExecutorService
1. implements Callable interface 2. override public T call() 3. create a fixed thread pool 4. create task with Future 5. submit the task with executor.submit(task) 6. check whether the task is done with isDone()
        class MyTask implements Callable{
            String fname;
            public MyTask(String fname){
                this.fname = fname;
            }
            public Integer call(){
                return wordCount(fname);
            }
        }

        ExecutorService executor = ExecutorService.newFixedThreadPool(10);
        for(String fname : ls){
            Future future = executor.submit(() -> wordCount(fname));
            if(future.isDone()){
                p("wordCount=" + future.get());
            }
        }
        
Java Simple Thread
A simple thread can be implemented Runnable interface and override run() method run() CAN NOT return any value, and CAN NOT throw any Exception
        public class HelloThread implements Runnable{
            public int num;
            public HelloThread(int num){
                this.num = num;
            }
            public void run(){
                for(int i=0; i<10; i++){
                    this.num += 1;
                    System.out.println("num=[" + num + "]");
                }
            }

            public static void main(String[] args) {
                Thread[] array = new Thread[10];
                for(int i=0; i<10; i++){
                    array[i] = new Thread(new HelloThread(1)); 
                    array[i].start();
                }
            }
        }
        
Java Synchronize method 1: keyword synchronized
            synchronized void fun(){
                count++;
                queue.add(count);
            }
            
Java Synchronize method 2: lock the current this object
            void fun(){
                synchronized(this){
                    count++;
                    queue.add(count);
                }
            }
            
Java Synchronize method 3: create locked object
            private Object lock1 = new Object();
            private Object lock2 = new Object();
            private long c1;
            private long c2;
            void fun(){
                synchronized(lock1){
                    c1++;
                }

                synchronized(lock2){
                    c2++;
                }
            }
            
Java Create simple thread 1: synchronized the method 2: implements Runnable interface, and override run()
            class Account{
                int sum = 0;
                Queue q;

                public void Account(){
                    Queue q = new LinkedList();
                }
                public synchronized void add(){
                    sum++;
                    q.add(sum);
                }
            }
            class MyThread implements Runnable{
                Account acc;
                public MyThread(Account acc){
                    this.acc = acc;
                }
                public void run(){
                    acc.add();
                }
            }

            // spawn num_threads
            Account acc = new Account();
            for(int i=0; i < num_threads; i++){
                Thread t = new Thread(new MyThread(acc));
                t.start();
            }
            
sleep(), wait(), notify() and notifyall() in Java
            sleep() - is static method, it can be used in the current thread.
                    - a sleeping thread can be awaked by interrupt or time expires 
            wait()  - each object has wait() method, and wait() can be used in synchronized block only.
                    - put the thread to sleep state and release the lock or monitor so that other thread can execute it
                    - a waiting thread can awaked by notify or notifyall
            notify()- each object has notify/notify, and it can be used in synchronized block only.
            
Java Join Thread, Join waiting for the thread until it die
            class TestJoin extends Thread{
                public void run(){
                    for(int i=0; i<5; i++){
                        try {
                            Thread.sleep(500);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                        System.out.println("[id=" + getId() + " name=" + getName() + "]["+i+"]");
                    }
                }
            }

            public class JoinThread {
                public static void main(String[] args) {
                    test1();
                }
                static void test1(){
                    Aron.beg();
                    TestJoin t1 = new TestJoin();
                    TestJoin t2 = new TestJoin();
                    TestJoin t3 = new TestJoin();

                    t1.start();
                    try{
                        t1.join(1500);
                    }catch(Exception e){
                    }

                    t2.start();
                    t3.start();

                    Aron.end();
                }
            }
        
Conditional variables, Condition(), await(), signal() in Java
            await() - 1. notFull.await(), release the lock associated with notFull, 
                      2. disable the current thread. 

            Lock lock = new ReentrantLock();
            Condition notFull = lock.newCondition();
            Condition notEmpty = new lock.newCondition();

            void get(){ // not empty
                lock.lock();
                try{
                    while(queue.size() == 0)
                        notEmpty.await();  

                    x = queue.poll();
                    notFull.signal();
                }finally{
                    lock.unlock();
                }
            }

            void put(int x){ // not full
                lock.lock();
                try{
                    while(queue.size() == MAx)
                        notFull.await();

                    queue.add(x);
                    notEmpty.signal();
                }finally{
                    lock.unlock();
                }
            }
            
CountDownLatch() in Java
    
Lock, Compare And Swap
    class MyLock{
        private boolean isLocked = false;
        public synchronized boolean lock(){
            if(!isLocked){
                isLocked = true;
                return isLocked;
            }
            return false;
        }
        public synchronized void unlock(){
            isLocked = false;
            notify();
        }
    }