JavaScript的对象是以一个描述ID、一个内容指针、以及跟随该对象的属性进行储存的。
当对象构造简单时,内容指针并不起作用,而所有属性直接跟在对象的内存地址之后。
比如对象{a: 1, b: 2},若其内存地址为0x1000,则该对象在内存中为
|0x1000|0x1008|0x1010|0x1018|
|---|---|---|---|
|描述ID|指针(空)|a|b|
不同于大多数语言,该指针指向的地址是同时向左右两个方向进行储存该对象的属性。由于这种对称的特性,很多人将JavaScript的内容指针称之为蝴蝶(Butterfly)。
当对象类型复杂时,比如对象包含7个以上的属性,那么butterfly就会起到作用
比如对象{a: 1, b: 2, c: 3, d: 4, e: 5, f: 6, g: 7},若其内存地址为0x1000,则该对象在内存中为
|0x1000|0x1008|
|---|---|
|描述ID|butterfly|
若该butterfly指向0x8000,则该地址内存构造大致为:
|0x7ff0|0x7ff8|0x8000(butterfly)|0x8008|0x8010|0x8018|0x8020|0x8028|
|---|---|---|---|---|---|---|---|
|-|g|a|b|c|d|e|f|
而当一个对象为数组时,该数组的butterfly一般为:
|0x7ff0|0x7ff8|0x8000(butterfly)|0x8008|0x8010|0x8018|
|---|---|---|---|---|---|
|-|length|元素1|元素2|元素3|元素4|
如果你给这个数组加一些其他的属性,比如arr.a = 1; arr.b = 2,那么该对象的butterfly就会变成
|0x7fe0|0x7fe8|0x7ff0|0x7ff8|0x8000(butterfly)|0x8008|0x8010|0x8018|
|---|---|---|---|---|---|---|---|
|-|b|a|length|元素1|元素2|元素3|元素4|
Most helpful comment
JavaScript的对象是以一个描述ID、一个内容指针、以及跟随该对象的属性进行储存的。
当对象构造简单时,内容指针并不起作用,而所有属性直接跟在对象的内存地址之后。
比如对象
{a: 1, b: 2},若其内存地址为0x1000,则该对象在内存中为|0x1000|0x1008|0x1010|0x1018|
|---|---|---|---|
|描述ID|指针(空)|a|b|
不同于大多数语言,该指针指向的地址是同时向左右两个方向进行储存该对象的属性。由于这种对称的特性,很多人将JavaScript的内容指针称之为蝴蝶(Butterfly)。
当对象类型复杂时,比如对象包含7个以上的属性,那么butterfly就会起到作用
比如对象
{a: 1, b: 2, c: 3, d: 4, e: 5, f: 6, g: 7},若其内存地址为0x1000,则该对象在内存中为|0x1000|0x1008|
|---|---|
|描述ID|butterfly|
若该butterfly指向
0x8000,则该地址内存构造大致为:|0x7ff0|0x7ff8|0x8000(butterfly)|0x8008|0x8010|0x8018|0x8020|0x8028|
|---|---|---|---|---|---|---|---|
|-|g|a|b|c|d|e|f|
而当一个对象为数组时,该数组的butterfly一般为:
|0x7ff0|0x7ff8|0x8000(butterfly)|0x8008|0x8010|0x8018|
|---|---|---|---|---|---|
|-|length|元素1|元素2|元素3|元素4|
如果你给这个数组加一些其他的属性,比如
arr.a = 1; arr.b = 2,那么该对象的butterfly就会变成|0x7fe0|0x7fe8|0x7ff0|0x7ff8|0x8000(butterfly)|0x8008|0x8010|0x8018|
|---|---|---|---|---|---|---|---|
|-|b|a|length|元素1|元素2|元素3|元素4|