这是怎么一回事? 它解决了什么问题? 什么时候合适,什么时候不合适?
18个答案
它创建一个新对象。 此对象的类型很简单 对象 . 它设置这个新对象的内部不可访问, [[原型]] (即。 __原型__ )属性作为构造函数的外部、可访问、, 原型 对象(每个函数对象自动具有 原型 属性)。 它使 这 变量指向新创建的对象。 它执行构造函数,在任何时候都使用新创建的对象 这 提到。 它返回新创建的对象,除非构造函数返回非- 无效的 对象引用。 在这种情况下,将返回该对象引用。
新建ConstructorFunction(arg1,arg2)
ObjMaker=function(){this.a='first';}; //“ObjMaker”只是一个函数,没有什么特别的 //这使它成为一个构造函数。 ObjMaker.prototype.b=“第二个”; //与所有函数一样,ObjMaker有一个可访问的“prototype”属性 //我们可以改变。 我刚刚在其中添加了一个名为“b”的属性。例如 //所有对象,ObjMaker还有一个无法访问的`[[prototype]]`属性 //我们无能为力 obj1=新的ObjMaker(); //刚刚发生了3件事。 //创建了一个名为“obj1”的新空对象。 起初`obj1` //只是{}。 然后将`obj1`的`[[prototype]]`属性设置为当前 //`ObjMaker.prototype`的对象值 //分配了一个新的对象值,`obj1`的`[[prototype]]`不会更改,但您 //可以更改“ObjMaker.prototype”的属性以将 //`prototype`和`[[prototype]]`)。 已执行“ObjMaker”函数 //`obj1`代替`this`。。。 因此“obj1.a”被设置为“first”。 目标1.a; //返回“第一个” 对象1.b; //“obj1”没有名为“b”的属性,因此JavaScript会进行检查 //它是`[[原型]]`。 其`[[prototype]]`与`ObjMaker.prototype相同` //“ObjMaker.prototype”的属性名为“b”,值为“second” //返回“秒”
SubObjMaker=函数(){}; SubObjMaker.prototype=新ObjMaker();// 注意:此模式已弃用! //因为我们使用了“new”,SubObjMaker.prototype的[[prototype]]属性 //现在设置为ObjMaker.prototype的对象值。 //现代的方法是使用Object.create(),它是在ECMAScript 5中添加的: //SubObjMaker.prototype=Object.create(ObjMaker.trototype); SubObjMaker.prototype.c=“第三个”; obj2=新的SubObjMaker(); //obj2的[[prototype]]属性现在设置为SubObjMaker.prototype //请记住,SubObjMaker.prototype的[[prototype]]属性 //是ObjMaker.prototype。 现在obj2有了一个原型链! //obj2-->SubObjMaker.prototype--->对象生成原型 目标2.c; //从SubObjMaker.prototype返回“第三个” 对象2.b; //从ObjMaker.prototype返回“second” 目标2.a; //从SubObjMaker.prototype返回“first”,因为SubObjMaker.proptotype //是使用ObjMaker函数创建的,该函数为我们分配了
-
53 只想补充一下:实际上有一种方法可以通过__proto__访问内部[[原型]]。 然而,这是非标准的,只有相对较新的浏览器(并非所有浏览器)才支持。 有一种标准化的方法即将出现,即Object.getPrototypeOf(obj),但它是Ecmascript3.1,而且它本身也只在新浏览器上受支持。 通常建议不要使用该属性,因为里面的东西很快就会变得复杂。 – 蓝色 评论 2011年4月14日14:55 -
12 -
15 @孤独像素 新的 存在 这样你就不必 编写工厂方法来构造/复制函数/对象。 它的意思是,“复制它,使它就像它的父‘类’一样;高效且正确地这样做;并存储只有我JS才能在内部访问的继承信息”。 为此,它修改否则无法访问的内部 原型 以不透明方式封装继承的成员,模仿经典的OO继承链(不可在运行时修改)。 你可以在没有 新的 ,但继承将在运行时可修改。 好吗? 不好? 由你决定。 – 工程师 评论 2012年10月23日22:36 -
12 -
7
var Foo=函数(){ 这个。 A=1; 这个。 B=2; };
Foo();
var bar=新Foo();
-
8 -
4 -
三 -
三 @金牛座在网络浏览器中,非方法函数将是 窗口 隐式地。 即使是在结尾,即使是匿名。 然而,在示例中,它是对窗口的一个简单方法调用: Foo(); => [默认上下文]。 Foo(); => 窗口。 Foo(); 。在此表达式中 窗口 是 上下文 (不仅仅是 呼叫者 ,这无关紧要)。 – 达维德·霍瓦思 评论 2017年9月11日11:47 -
2
函数新建(func){ var res={}; if(函数原型!==空){ res.__proto__=功能原型; } var ret=func.apply(res,Array.prototype.slice.call(arguments,1)); if((typeof ret===“object”||typeof ret===”function“)&&ret!== null){ 返回ret; } 返回res; }
var obj=新(A,1,2);
var obj=新的A(1,2);
-
79 -
1 -
7 @您可以通过简单地编写以下代码来覆盖prototype属性 A.原型=空; 在这种情况下 新A() 将导致on对象,即内部原型指向 对象 对象: jsfiddle.net/Mk42Z – 巴西利库姆 评论 2014年4月28日18:19 -
三 -
三 @Oriol感谢您的评论。 你说的没错,任何实际测试都应该以更稳健的方式进行。 然而,我认为对于这个概念性的答案 类型 测试只是让人们更容易理解幕后发生的事情。 – 巴西利库姆 评论 2015年10月8日21:53
让初学者更好地理解
函数Foo(){ 返回此; } var a=Foo();// 返回“window”对象 var b=新Foo();// 返回foo的空对象 Window的一个实例;// 真的 Foo的一个实例;// False(错误) b Window实例;// False(错误) b Foo实例;// 真的
所以这可能不是为了创造 对象的实例
职能人员(姓名){ this.name=名称; } var john=新人(“john”);
Person.prototype.getName=函数(){return this.name;}
-
8 -
2 -
12
总结:
创建新对象 将此对象的原型设置为构造函数的原型属性 绑定 这 关键字添加到新创建的对象并执行构造函数 返回新创建的对象
例子:
功能狗(年龄){ this.age=年龄; } const doggie=新狗(12); 控制台日志(doggie); console.log(Object.getPrototypeOf(doggie)===Dog.prototype)//true
康斯特小狗 说:我们需要内存来声明变量。 赋值运算符 = 表示:我们将使用 = 表达式是 新狗(12) 。JavaScript引擎会看到 新的 关键字,创建新对象并将原型设置为 狗.原型 构造函数用 这 值设置为新对象。 在此步骤中,年龄被指定给新创建的小狗对象。 新创建的对象将返回并分配给变量doggie。
var Foo=函数(){ 这个。 A=1; 这个。 B=2; }; console.log(Foo())// 打印未定义 console.log(window.A)// 打印1
var Foo=函数(){ 这个。 A=1; 这个。 B=2; 返回未定义; }; console.log(Foo())// 打印未定义 console.log(window.A)// 打印1
var Foo=函数(){ 这个。 A=1; 这个。 B=2; }; var bar=新Foo(); console.log(bar())// 非法不是指向函数而是指向对象 控制台.log(bar.A)// 打印1
var Foo=函数(){ 这个。 A=1; 这个。 B=2; 返回{C:20,D:30}; }; var bar=新Foo(); 控制台.log(bar.C)// 打印20 控制台.log(bar.A)// 打印未定义。 bar没有指向由于new关键字而创建的对象。
计算对象创建表达式时,JavaScript首先 创建一个新的空对象,就像对象创建的对象一样 初始化器{}。 接下来,它使用 指定的参数,将新对象作为this的值传递 关键字。 然后,函数可以使用它来初始化属性 新创建对象的。 编写用作构造函数的函数 不返回值,以及对象创建表达式的值 是新创建和初始化的对象。 如果构造函数这样做 返回一个对象值,该值将成为对象的值 创建表达式,则丢弃新创建的对象。
var func1=函数(x){this.x=x;}//仅与“new”一起使用 var函数2=函数(x){var z={}; z.x=x; 返回z;}// 双向使用 func1.prototype.y=11; 函数2.prototype.y=12; A1=新函数1(1);// 有A1.x和A1.y A2=函数1(1);// 未定义(“此”指“窗口”) B1=新函数2(2);// 仅具有B1.x B2=函数2(2);// 只有B2.x
常量a={name:“某物”}; console.log(a.prototype);//' “undefined”,因为它不能直接访问 常数b=函数(){ console.log(“somethin”); }; console.log(b.prototype);// 返回b{}
控制台.log(a.__proto__);// 返回{} 控制台.log(b.__proto__);// 返回[函数]
函数CreateObject(名称、年龄){ this.name=名称; this.age=年龄 }
使用调用构造函数时 新的 ,调用函数的内部[[Construct]]方法来创建新的实例对象并分配内存。 我们没有使用 返回 关键字。 新的 将处理它。 函数名是大写的,因此当开发人员看到您的代码时,他们可以理解他们必须使用 新的 关键字。 我们不使用箭头功能。 因为 这 参数是在创建箭头函数时拾取的,即“ 窗口 。箭头函数的范围是词汇上的,而不是动态的。这里的词汇表示本地。箭头函数带有其本地“this”值。 与常规函数不同,不能使用new关键字调用箭头函数,因为它们没有[[Construct]]方法。 箭头函数也不存在原型属性。 const me=new CreateObject(“yilmaz”,“21”) 新的 调用该函数,然后创建一个空对象{},然后添加值为“name”的“name”键,以及值为参数“age”的“age”键。
函数CreateObject(名称、年龄){ this.name=名称; this.age=年龄; const myJob=“开发人员” }
constme={name:“yilmaz”,age:21}//没有任何“myJob”键
CreateObject.prototype.myActions=函数(){/*定义内容*/}
const a=新编号(5); 控制台.log(a);// [编号:5] console.log(类型a);// 对象
常数b=5; console.log(a===b);//' 假'
-
-
我必须用英语写作,否则会被认为是骗局:)课堂就像一个工厂。 想象一下像一个汽车工厂。 每辆车都有自己的特性和方法:比如颜色,有四个轮子,有一个马达等等。所以建造师是你建造汽车的地方,就像工厂的生产单元一样。 无论何时创建新汽车,汽车的特定属性都将在构造函数中生成。 例如,并不是所有的汽车都有相同的颜色。 所以我们在建造或启动汽车时会传递颜色。 所以每辆车都会有颜色,所以会在制造商中指定 – 伊尔马兹 评论 2020年9月1日17:31 -
构造函数中的属性将存储在car对象或car实例中。 假设您构造了1000个car实例,这将占用太多空间。 因此,每辆车的共同属性都是在构造函数之外指定的。 例如,每辆车都有四个轮子。 所以它存储在原型中。 属性存储在原型中,而不是存储在每个汽车对象中。 相反,它将存储在一个地方,您将在需要时使用它。 这被称为原型遗传。 我希望我的解释足够清楚:) – 伊尔马兹 评论 2020年9月1日17:35 -
-
{ //其他属性 原型:{ //自动获取[[原型]]链接的共享空间 当“new”关键字用于创建“Constructor”实例时 功能“ } }
手动创建对象,例如newObj。 使用创建隐藏债券 原型 (又名: 扣篮 原型 )在JavaScript规范中 [[原型]] (即。, 原型 ) 引用并将属性指定给 新建对象 返回 新建对象 对象。
函数CreateObj(值1,值2){ const newObj={}; newObj.properties 1=值1; newObj.property2=值2; return newObj; } var obj=创建对象(10,20); obj.__proto__===对象原型;// 真的 Object.getPrototypeOf(obj)===对象原型//真
创建一个新的对象文字,标识为 此:{} 引用并将属性指定给 这 隐性债券创建 [[原型]](即。 原型 ) 到 功能.原型 共享空间。 隐式回报 这 对象{}
函数CreateObj(值1,值2){ this.property1=值1; this.property2=值2; } var obj=新CreateObj(10,20); obj.__proto__===创建对象原型//真 Object.getPrototypeOf(obj)==CreateObj.prototype//真
函数CreateObj(值1,值2){ var isWindowObj=this===窗口; console.log(“正在指向窗口对象”,isWindowObj); this.property1=值1; this.property2=值2; } var obj=新CreateObj(10,20);// 指向窗口对象为false var obj=创建对象(10,20);// 指向窗口对象为true 窗口属性1;// 10 窗口属性2;// 20
var Foo=函数(){}; Foo.prototype.bar=“bar”; var foo=新foo(); foo的foo实例;// 真的
foo.bar;//' 巴'
-
2 新关键字基本上已经将函数关联为构造函数; 你不需要归还任何东西。 您只需执行以下操作:函数foo(x){this.bar=x;}var obj=new foo(10); 警报(obj.bar); – 请求(t) 评论 2009年10月29日21:40 -
您不需要从构造函数返回对象,除非您出于某种目的特别希望这样做。 例如,如果您必须返回一个特定的对象实例,而不是每次都创建一个新对象(无论出于何种原因)。 然而,在您的示例中,这是完全不必要的。 评论 2009年10月29日21:43 -
ECMAScript是一种面向对象的编程语言,用于 执行计算和操作计算对象 在主机环境中。
ECMAScript不使用C++、Smalltalk或Java中的类。 相反,可以通过多种方式创建对象,包括通过 文字符号或via构造函数,它创建对象,然后执行代码,通过指定初始值来初始化全部或部分对象 值设置为其属性。 每个构造函数都是一个具有 名为―的属性 prototype‖,用于实现基于原型的继承和共享属性。 对象由创建 在新表达式中使用构造函数; 例如,new Date(2009,11)创建一个新的Date对象。 调用构造函数 不使用new的结果取决于构造函数。 例如,Date()生成 当前日期和时间,而不是对象。
函数myNew(构造函数,…args){ 常量对象={} Object.setPrototypeOf(obj,constructor.prototype) const returnedVal=构造函数.apply(obj,args) 如果( returnedVal===“函数”的类型 ||(returnedVal的类型===“对象”&&returnedVal!==空){ 返回returnedVal } 返回对象 }
函数MyClass(){ this.name=“卡兹!” this.init=()=>{ console.log('I am init func') } }
let obj=新MyClass() 对象初始化() 控制台.log(对象名称)。// 打印“Kazi!”