规定执行的子线程数
    只有满足所规定的子线程数都执行完毕后 主线程才能执行
    否则主线程会一直等待
    原理其实是通过-1操作来实现的 即使没有线程 直接执行-1操作也行
    直到将所规定的数减至0即可

    1. public static void main(String[] args) throws Exception {
    2. final CountDownLatch cdl = new CountDownLatch(4);
    3. //这里定义四个子线程数
    4. //每个线程执行完后 执行减一操作 直到减到0 主线程才能执行
    5. new Thread(new Runnable() {
    6. @Override
    7. public void run() {
    8. try {
    9. Thread.sleep(3000);
    10. } catch (InterruptedException e) {
    11. e.printStackTrace();
    12. }
    13. System.out.println("购买海鲜");
    14. cdl.countDown();
    15. //执行-1操作
    16. }
    17. }).start();
    18. new Thread(new Runnable() {
    19. @Override
    20. public void run() {
    21. System.out.println("购买牛羊肉");
    22. try {
    23. Thread.sleep(1000);
    24. } catch (InterruptedException e) {
    25. e.printStackTrace();
    26. }
    27. cdl.countDown();
    28. //执行-1操作
    29. }
    30. }).start();
    31. new Thread(new Runnable() {
    32. @Override
    33. public void run() {
    34. System.out.println("购买火锅底料和蘸料");
    35. try {
    36. Thread.sleep(800);
    37. } catch (InterruptedException e) {
    38. e.printStackTrace();
    39. }
    40. cdl.countDown();
    41. //执行-1操作
    42. }
    43. }).start();
    44. new Thread(new Runnable() {
    45. @Override
    46. public void run() {
    47. System.out.println("购买青菜");
    48. try {
    49. Thread.sleep(2000);
    50. } catch (InterruptedException e) {
    51. e.printStackTrace();
    52. }
    53. cdl.countDown();
    54. //执行-1操作
    55. }
    56. }).start();
    57. // 等待食材购买完成
    58. cdl.await();
    59. //如果此时只有三个线程执行了减一操作 那么这个方法就会一直阻塞等待 直到执行了第四个减一操作
    60. System.out.println("开始吃火锅!!");
    61. }