Hot Reload 只能在 Debug 模式下使用,是因为 Debug 模式下,Flutter 采用的是 JIT 动态编译,代码是运行在 Dart VM 上,JIT 将 Dart 编译成可以运行在 Dart VM 上的 Dart Kernel,Dart Kernel 可以动态更新,所以就实现了代码的实时更新功能。
当调用 Hot Reload 时:
- 首先会扫描代码,找到上次编译之后有变化的 Dart 代码。
- 在将这些变化的 Dart 代码转化为增量的 Dart Kernel 文件。
- 将增量的 Dart Kernel 文件发送到正在移动设备上运行的 Dart VM。
- Dart VM 会将发来的增量 Dart Kernel 文件和原有的 Dart Kernel 文件合并,然后重新加载全新的 Dart Kernel。
- 这个时候,虽然重新加载了 Dart Kernel,却不会重新执行代码,而是通知 Flutter Framework 重建 Widget。
所以 Flutter 的 Hot Reload 并不会重新执行一遍代码,而是触发 Flutter 重新绘制,并且会保留 Flutter 之前的状态,所以 Hot Reload 也被称为有状态的热重载。
JIT(Just-In-Time)动态编译是一种编译技术
JIT(Just-In-Time)动态编译是一种编译技术,它在程序运行时将某些代码编译成机器语言,而不是在程序安装时或编译时进行编译。这样做的好处是可以在运行时根据运行环境和程序使用情况进行优化,从而提高程序的运行效率。
JIT 编译通常用于解释型语言(如 Python、JavaScript 等),因为这些语言在运行时会解释代码,使用 JIT 动态编译可以提高解释型语言的运行效率。
JIT 编译的工作流程如下:
- 解释器将解释到的代码加载到内存中。
- 解释器运行代码,如果发现某些代码被频繁使用,就将这些代码送到 JIT 编译器进行编译。
- JIT 编译器将代码编译成机器语言,并将编译后的代码加载到内存中。
- 解释器在运行代码时,如果发现某段代码已经被编译,就直接调用编译后的代码,而不再解释执行。