2020-02-27
關鍵字:
筆者遇到一個因 GC 而引發的監聽無效的問題。
今天遇到個需求:需要監聽某個文件的狀態。
於是在網上找到答案,原來 Android 默認就提供了一個 android.os.FileObserver 的功能,可以監聽文件系統中指定文件或文件夾的各種訪問事件。
關於 FileObserver 的使用,筆者主要參考了這兩篇博客:
https://www.jianshu.com/p/a509ad4311c0
https://blog.csdn.net/Tony_YY/article/details/89688438
但是,當筆者親自寫代碼來驗證的時候,卻發現當受監聽的文件的狀態改變了以后,FileObserver 的 onEvent() 方法死活不會回調的問題。筆者加過各種打印,也更換過種種文件位置,均發現 FileObserver 無法監聽。
遍尋百度無果,萬般無奈之下看了 android 官方關於 FileObserver 的文檔:
https://developer.android.google.cn/reference/android/os/FileObserver.html
終於在文檔中看到一句警告,如下圖所示:
這句警告大致的意思是:建議創建一個生命周期比較長的變量來存儲你的 FileObserver 實例,否則有可能發生實例被 GC 回收的情況,一旦 FileObserver 實例被回收了,就無法監聽了。
醍醐灌頂!
翻看一下筆者的代碼,筆者當時貪方便,直接以下面的形式來啟動文件監聽:
new HDMIWatcher().startWatching();
這樣創建出來的實例,顯示有很大的幾率被 GC 回收掉。
於是改成用一個全局變量的儲存實例引用的方式:
watcher = new HDMIWatcher(); watcher.startWatching();
再次驗證,發現問題已經沒有了。
還是官方文檔好啊。