关于反应式声明
$: doubled = count*2
,它在svelte tutorial中指出
别担心,这看起来是否有点陌生。这是有效的(如果是非常规的)JavaScript,Svelte会将其解释为“只要任何引用的值发生更改,便重新运行此代码”
常规的javascript功能引用似乎是labels(请确认)
请用简单的词解释svelte编译器是如何完成的,并提供对编译器代码中发生这种情况(或开始发生)的位置的引用
有一个githb issue可以解释最终的苗条内部构造。
答案 0 :(得分:8)
这确实是标签语法。
Javascript标签几乎没有用处,因此这是一种创建简单语法以及确保其与linters和IDE兼容的绝佳方法。
您在哪里可以找到代码:
代码编译后,您可以在组件生命周期的状态更新部分中找到反应式声明。但是,在与 DOM更新相关的beforeUpdate和afterUpdate之间不会执行此代码。如果您在这些回调中更改值,则可能会得到一些古怪的结果,因为反应式语句可能不会更新。
如果您寻找$$self.$$.update
,则可以在代码中找到它。
工作方式:
编译器正在分析这些语句以查找要观察哪些变量的更改。这些变量是赋值运算符或函数调用中的每个参数的所有权利。值得注意的是,没有观察到const变量,因为它们永远都不会改变。
$: doubled = count * 2;
将编译为
if ($$dirty.count) { $$invalidate('doubled', doubled = count * 2); }
$$ dirty是更新生命周期接收到的参数,它是一个对象,其中包含每个可能修改的变量的属性,在调用$$invalidate
时将其设置为1。
Svelte然后在生命周期的更新部分的末尾添加这些语句,并根据至少一个上述观察到的变量的变化来限制其执行。
Svelte还按照拓扑顺序对这些语句进行排序。这意味着将在之后评估使用另一个反应式语句结果的反应式语句。不管您以何种顺序将它们放入代码中。
$: quadrupled = doubled * 2;
$: doubled = count * 2;
仍将正确编译为
if ($$dirty.count) { $$invalidate('doubled', doubled = count * 2); }
if ($$dirty.doubled) { $$invalidate('quadrupled', quadrupled = doubled * 2); }
希望它有助于清除问题。