天天看點

關于final修飾符的一些小坑

關于final修飾符的一些小坑

今天在測試JUC包的CyclicBarrier方法的時候,遇到一個關于jfinal的問題
 
import java.util.concurrent.CyclicBarrier;

public class CyclicBarrierDemo {

    public static void main(String[] args) {
     
        CyclicBarrier cyclicBarrier = new CyclicBarrier(7,()->{
            System.out.println("運作到最後");
        });
        for (int i = 0; i < 7; i++) {
        
            final int tmp = i;
            
            new Thread(()->{
           		 //這裡引用tmp 需要tmp是final修飾的 在JDK1.8之後,不使用final也可以,但tmp的值不能改變,因為JDK1.8在編譯的時候做了處理
                System.out.println(tmp);   
                try {
                    cyclicBarrier.await();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                } catch (BrokenBarrierException e) {
                    e.printStackTrace();
                }
            }).start();
        }
    }
}
這裡的tmp如果需要在匿名内部類中使用,那麼需要final關鍵字修飾,在JDK1.8中進行了優化處理,可以不加,但是不允許值發生改變
在匿名内部類中通路局部變量,那麼這個局部變量必須用final修飾

           

為什麼需要用final修飾呢?

  1. 因為為了保護資料的一緻性,對于基本類型如(int)來說的就是值的一緻性,對于引用變量來說的,就是引用位址的一緻性
  2. 如果不使用final進行修飾,那麼原先的局部變量可以發生變化,那麼匿名内部類在引用的時候就會出錯
  3. 因為最開始建立匿名内部類後,值是在匿名内部類的構造器中進行指派傳入的,是以後續代碼的修改,會導緻程式最終結果不一緻