本机对象和宿主对象有什么区别?

IT技术 javascript javascript-objects
2021-01-13 12:20:06

我不明白JavaScript 中本机对象宿主对象之间的区别后者是否只是指由自定义构造函数(例如,var bird1 = new Bird();创建的非原始函数对象

6个回答

这两个术语都在 ECMAScript 规范中定义:

本机对象

ECMAScript 实现中的对象,其语义完全由本规范定义,而不是由宿主环境定义。

注:本规范中定义了标准本机对象。一些本机对象是内置的;其他的可能会在 ECMAScript 程序的执行过程中被构造。

来源:http : //es5.github.com/#x4.3.6

宿主对象

宿主环境提供的对象来完成ECMAScript的执行环境。

注意任何非本机对象都是宿主对象。

来源:http : //es5.github.com/#x4.3.8


几个例子:

本机对象:(Object构造函数)、DateMathparseIntevalindexOf等字符串方法replace、 数组方法、 ...

宿主对象(假设浏览器环境):window, document, location, history, XMLHttpRequest, setTimeout, getElementsByTagName, querySelectorAll, ...

自定义 custructor 怎么样?例如,我帖子中的鸟类示例
2021-03-16 12:20:06
也给他一些例子,原生对象:数组,字符串..,宿主对象:窗口......
2021-03-17 12:20:06
@ŠimeVidas,我不同意,如果Bird是用户定义的函数,它的语义是由 ES 规范“完全定义”的(函数对象如何工作,它们如何创建、执行、与new运算符一起使用等,等等)它是一个本机对象......我可能会放弃一个答案......
2021-04-04 12:20:06
@ŠimeVidas:“那么它就是一个宿主对象。” 那不正确。请参阅此答案host object描述的定义
2021-04-06 12:20:06
ŠimeVidas:但规范声明宿主对象的 [[Class]] 内部属性的值可以是任何字符串值,除了“Arguments”、“Array”、“Boolean”、“Date”、“Error”、 “函数”、“JSON”、“数学”、“数字”、“对象”、“RegExp”和“字符串”。Bird 对象的内部 [[Class]] 属性将是'Object',或通过Object.prototype.toStringas呈现'[object Object]'
2021-04-13 12:20:06

如果我们区分三种对象就更清楚了:

内置对象StringMathRegExpObjectFunction等-核心预定义的对象总是可以在JavaScript中。在 ECMAScript 规范中定义。

宿主对象windowXmlHttpRequest、 DOM 节点等对象由浏览器环境提供。它们不同于内置对象,因为并非所有环境都具有相同的宿主对象。如果 JavaScript 在浏览器之外运行,例如作为 Node.js 中的服务器端脚本语言,则不同的主机对象将可用。

用户对象:在 JavaScript 代码中定义的对象。因此,您示例中的“Bird”将是一个用户对象。

JavaScript 规范将内置对象和用户对象组合为原生对象这是术语“本机”的非正统用法,因为用户对象显然是用 JavaScript 实现的,而内置对象很可能是在底层用不同的语言实现的,就像宿主对象一样。但是从 JavaScript 规范的角度来看,内置对象和用户对象都是 JavaScript 原生的,因为它们是在 JavaScript 规范中定义的,而宿主对象不是。

本机对象是指由 javascript 实现(引擎)创建的那些对象。内置对象和其他原生对象(用户对象)之间的区别在于,从 JavaScript 程序开始就存在符合相关 ECMA 规则的以前的对象。由于 ECMA6 (<ECMA6 ecma-international.org/publications/files/ECMA-ST/... ),它不使用上述术语对对象进行分类。参考我下面的回答。
2021-03-27 12:20:06

这是我对规范的理解。

这:

var bird = new Bird();

...导致使用new操作符刚好创建的本机对象

本机对象具有以下之一的内部 [[Class]] 属性:

“参数”、“数组”、“布尔值”、“日期”、“错误”、“函数”、“JSON”、“数学”、“数字”、“对象”、“RegExp”和“字符串”

对于您bird1来说,它将是:

“目的”

就像你创建一个函数一样:

function my_func() {
    // ...
}

...my_func在 ECMAScript 中没有定义,但它仍然是一个具有内部 [[Class]] 的本机对象:

“功能”

宿主对象是环境提供的对象,目的是为规范中未定义的环境提供特定目的。

例如:

var divs = document.getElementsByTagName('div')

引用的对象divs是一个NodeList,它以一种感觉就像一个常规 JavaScript 对象的方式集成到环境中,但它没有被规范定义在任何地方。

它的内部 [[Class]] 属性是:

“节点列表”

这为实现设计者在使实现适应环境的特定需要方面提供了一些灵活性。

整个规范中都定义了宿主对象的要求

谢谢@CMS。是的,我并不是想过分强调使用内部[[Class]]. 而只是将其用作实现者如何解释不同类型对象的有形一瞥。那么window.alert,内部的[[Class]]of"Function"似乎违反了 ES 5?
2021-03-14 12:20:06
这很有帮助获取所有内容window显示所有主机对象
2021-03-17 12:20:06
+1,我同意你的看法,bird并且Bird原生对象,它们是用户定义的函数(Bird),以及bird使用该函数作为构造函数创建的对象(),所有这些语义都在规范中定义。关于宿主对象,不要太依赖[[Class]]内部属性,比如几乎所有的实现window.alert都有"Function"作为它的[[Class]]属性的值,在IE上它有"Object",而且它仍然是一个宿主对象......
2021-03-23 12:20:06
Bird 不是原生对象,因为它的接口在 ECMASCRipt 标准中没有完全描述。真的就是这么简单。对象是本机的,字符串是本机的,但用户定义的或主机定义的对象不是本机的。
2021-03-27 12:20:06
我试图看到这个动作,但是如果我得到那个 div 的类型divs/NodeList,我得到一个object. 我猜我还不明白这一点,但这不会使它成为本机对象吗?
2021-04-02 12:20:06

除了有关主机对象的其他答案。

宿主对象特定于环境。所以在浏览器的宿主对象旁边,还有 nodejs 中的特定对象。

就示例而言,首先从 Javascript 中定义的标准对象开始。然后是浏览器/DOM 的公共对象。节点有它自己的对象。

  1. 标准 Javascript内置对象示例:
  1. 宿主对象文档对象模型示例:
  1. Node.js 中的宿主对象

对于var bird1 = new Bird();是本机对象还是宿主对象的问题,看不到令人信服的答案假设Bird是一个用户定义的函数,javascript实现会根据http://es5.github.io/#x13.2创建一个原生的非内置对象相比之下,原生内置对象将在 javascript 程序(例如 Object 和许多其他程序)启动后出现。本机对象和宿主对象的区别在于,前者是由 javascript 实现创建的,而后者是由宿主环境提供的。因此,宿主对象内部 [[class]] 属性可能与内置对象使用的属性不同(即“参数”、“数组”、“布尔值”、“日期”、“错误”、“函数”、“ JSON”、“数学”、“数字”、“对象”、“RegExp”和“字符串”)。

另外,值得注意的是 ECMA6 http://www.ecma-international.org/publications/files/ECMA-ST/Ecma-262.pdf不再使用术语本机和主机对象。相反,它定义了以下对象类型,并对其预期行为进行了更清晰的解释。

4.3.6 普通对象

具有所有对象必须支持的基本内部方法的默认行为的对象

4.3.7 异物

不具有所有对象必须支持的一个或多个基本内部方法的默认行为的对象 注意任何不是普通对象的对象都是奇异对象。

4.3.8 标准对象

其语义由本规范定义的对象

4.3.9 内置对象

由 ECMAScript 实现指定和提供的对象