繁体   English   中英

如何在 v8 中检查 object 属性是对象内属性、快速属性还是慢速属性?

[英]How do I inspect whether a object property is a in-object property, fast property, or slow property in v8?

帖子https://v8.dev/blog/fast-properties提到了三种属性。 我如何找出一个属性是哪一个?

我期待使用 v8 本机语法 function 或开发工具功能的答案。

(这里是 V8 开发人员。)

object 是否具有字典模式属性是每个对象(而不是每个属性)的决定。 替代方案 state 具有“快速”属性,这通常意味着对象内和对象外属性的混合。

任何使用--allow-natives-syntax运行的 V8 构建都可以使用%HasFastProperties(obj)来判断 object 是否具有“快速”属性(返回值为true )或字典属性( false )。

要查看“快速”模式 object 有多少个对象内属性,您需要调试版本,并使用%DebugPrint(obj)

据我所知,DevTools 不会公开此信息。 (恕我直言,这很好,因为除了好奇之外你不需要关心这个。)

旁注:我认为“快”和“慢”是非常具有误导性的描述,因为它们听起来太像“好案例”和“坏案例”,而实际上它们具有不同的优点和缺点。 使用隐藏的 class 跟踪其精确属性布局的对象在读取/写入现有属性的值时速度很快,但在添加/删除属性时非常慢。 使用字典作为其属性的对象在读取/写入属性值时稍慢,但在添加/删除属性时要快得多。 因此,根据您的应用程序的用例,您有时需要一个,有时需要另一个,除了病态情况外,引擎也非常擅长切换到一个或另一个,并且没有 object state 明显优于另一个。 (如果您知道您将添加和删除许多属性,那么使用Map将比使用普通对象提供更好的性能。)

这是对快速和慢速属性之间差异的长话短说。 在JS中创建一个object时,会附加一个隐藏的class。 当属性被添加到 object 时,“类转换”发生(旧的隐藏 class 切换到新的隐藏 class,其中包含新属性)

当 V8 看到一个 class 构造函数 function 被声明时,它创建一个隐藏的 class 例如:C0。 现在,当 V8 在下一行看到一个属性被添加时,在我们的例子中:name 它用新属性更新 C0 并从 C0 切换到一个新的隐藏 class 说 C1,然后它看到下一个属性:age 并切换到 C2 .

在此示例中,向 2 人对象动态添加新属性并不是优化的解决方案,因为两个新属性(喜欢和不喜欢)的实例化顺序不同。 不同的顺序会导致创建两个不同的隐藏类,而不是共享一个公共隐藏类 class。

所以:我们为构造函数 function 人创建 C0。 它过渡到 C1 的名字,然后是 C2 的年龄。 对于 person1,当它看到一个属性时“喜欢”并转换到 C3a,“不喜欢”到 C4a。 但是,对于 person2,V8 首先看到属性“不喜欢”被添加到它,因此它没有共享隐藏的 class C3a,而是创建了一个新的隐藏的 class C3b。 然后它为 C4b 等属性创建一个新的隐藏 class。

由于这两个对象不共享隐藏类(当它们本可以共享它们时); 访问 object 的属性很慢,因为 V8 现在无法使用内联缓存。 如果两者共享隐藏的 class,V8 将使用内联缓存来加快访问速度。 所以在下面的示例中,这些是慢速属性。 如果订单相同,本来会很快。

希望这个对你有帮助。

 function person(name,age) { this.name = name; this.age = age; } let person1 = new person("jim", 28); let person2 = new person("jane", 27); person1.likes = "games"; person1.dislikes = "running"; person2.dislikes = "cities"; person2.likes = "nature";

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM