Я смущаюсь, каким образом я должен создавать объект в javascript. Кажется, есть по крайней мере два пути. Один из них - использовать условное обозначение объекта, в то время как другое использует функции построения. Есть ли преимущество одного над другим?
Должен ли я использовать объектные литералы или функции конструктора?
Ответ 1
Если у вас нет поведения, связанного с объектом (т.е. если объект является просто контейнером для данных/состояния), я бы использовал литерал объекта.
var data = {
foo: 42,
bar: 43
};
Примените принцип KISS. Если вам не нужно ничего, кроме простого контейнера данных, перейдите к простому литералу.
Если вы хотите добавить поведение к своему объекту, вы можете пойти с конструктором и добавить методы к объекту во время построения или предоставить прототипу своего класса.
function MyData(foo, bar) {
this.foo = foo;
this.bar = bar;
this.verify = function () {
return this.foo === this.bar;
};
}
// or:
MyData.prototype.verify = function () {
return this.foo === this.bar;
};
Подобный класс также действует как схема для вашего объекта данных. Теперь у вас есть какой-то контракт (через конструктор), какие свойства инициализирует/содержит объект. Свободный литерал - это просто аморфный кадр данных.
У вас также может быть внешняя функция verify
, которая действует на простой старый объект данных:
var data = {
foo: 42,
bar: 43
};
function verify(data) {
return data.foo === data.bar;
}
Однако это не выгодно для инкапсуляции: в идеале все данные + поведение, связанное с сущностью, должны жить вместе.
Ответ 2
Это, по сути, сводится к тому, что вам нужно несколько экземпляров вашего объекта или нет; объект, определенный с помощью конструктора, позволяет иметь несколько экземпляров этого объекта. Объектные литералы представляют собой в основном одноточие с переменными/методами, которые являются общедоступными.
// define the objects:
var objLit = {
x: 0,
y: 0,
z: 0,
add: function () {
return this.x + this.y + this.z;
}
};
var ObjCon = function(_x, _y, _z) {
var x = _x; // private
var y = _y; // private
this.z = _z; // public
this.add = function () {
return x + y + this.z; // note x, y doesn't need this.
};
};
// use the objects:
objLit.x = 3;
objLit.y = 2;
objLit.z = 1;
console.log(objLit.add());
var objConIntance = new ObjCon(5,4,3); // instantiate an objCon
console.log(objConIntance.add());
console.log((new ObjCon(7,8,9)).add()); // another instance of objCon
console.log(objConIntance.add()); // same result, not affected by previous line
Ответ 3
Другим способом создания объектов в унифицированном виде является использование функции, возвращающей объект:
function makeObject() {
var that = {
thisIsPublic: "a public variable"
thisIsAlsoPublic: function () {
alert(that.thisIsPublic);
}
};
var secret = "this is a private variable"
function secretFunction() { // private method
secret += "!"; // can manipulate private variables
that.thisIsPublic = "foo";
}
that.publicMethod = function () {
secret += "?"; // this method can also mess with private variables
}
that.anotherPublicVariable = "baz";
return that; // this is the object we've constructed
}
makeObject.static = "This can be used to add a static varaible/method";
var bar = makeObject();
bar.publicMethod(); // ok
alert(bar.thisIsPublic); // ok
bar.secretFunction(); // error!
bar.secret // error!
Так как функции в JavaScript являются закрытиями, мы можем использовать частные переменные и методы и избегать new
.
От http://javascript.crockford.com/private.html от частных переменных в JavaScript.
Ответ 4
Это зависит от того, что вы хотите сделать. Если вы хотите использовать (semi-) частные переменные или функции в объекте, это может быть функция-конструктор. Если ваш объект содержит только свойства и методы, литерал объекта прекрасен.
function SomeConstructor(){
var x = 5;
this.multiply5 = function(i){
return x*i;
}
}
var myObj = new SomeConstructor;
var SomeLiteral = {
multiply5: function(i){ return i*5; }
}
Теперь метод multiply5
в myObj
и SomeLiteral
делает то же самое. Единственное отличие состоит в том, что myObj использует закрытую переменную. Последнее может быть полезно в некоторых случаях. В большинстве случаев достаточен литерал Object и хороший и чистый способ создания JS-объекта.
Ответ 5
В приведенном ниже коде показаны три метода создания объекта, синтаксис Object Literal, конструктор функций и Object.create()
. Литеральный синтаксис объекта просто создает и объект "на лету", и поэтому его __prototype__
является объектом Object
, и он будет иметь доступ ко всем свойствам и методам Object
. Строго с точки зрения шаблона проектирования должен использоваться простой литерал Object для хранения одного экземпляра данных.
Конструктор функции имеет специальное свойство с именем .prototype
. Это свойство станет __prototype__
любых объектов, созданных конструктором функции. Все свойства и методы, добавленные к свойству .prototype
конструктора функций, будут доступны всем объектам, которые он создает. Конструктор должен использоваться, если вам требуется несколько экземпляров данных или требуется поведение от вашего объекта. Обратите внимание, что конструктор функций также наилучшим образом используется, когда вы хотите имитировать шаблон частного/общего развития. Не забудьте поместить все общие методы в .prototype
, чтобы они не создавались в каждом экземпляре объекта.
Создание объектов с помощью Object.create()
использует объектный литерал как __prototype__
для объектов, созданных этим методом. Все свойства и методы, добавленные в литерал объекта, будут доступны для всех объектов, созданных из него через истинное прототипное наследование. Это мой предпочтительный метод.
//Object Example
//Simple Object Literal
var mySimpleObj = {
prop1 : "value",
prop2 : "value"
}
// Function Constructor
function PersonObjConstr() {
var privateProp = "this is private";
this.firstname = "John";
this.lastname = "Doe";
}
PersonObjConstr.prototype.greetFullName = function() {
return "PersonObjConstr says: Hello " + this.firstname +
" " + this.lastname;
};
// Object Literal
var personObjLit = {
firstname : "John",
lastname: "Doe",
greetFullName : function() {
return "personObjLit says: Hello " + this.firstname +
", " + this.lastname;
}
}
var newVar = mySimpleObj.prop1;
var newName = new PersonObjConstr();
var newName2 = Object.create(personObjLit);
Ответ 6
Перейдите с литералом объекта, он более конкретизируется и расширяется с введением начальных значений.
Ответ 7
//Object Literal и Object constructor
function MyData(foo, bar) {
this.foo = foo;
this.bar = bar;
}
MyData.prototype.verify = function () {
return this.foo === this.bar;
};
//add property using prototype
var MD = new MyData;//true.
var MD = new MyData();//true.
MD.verify// return only the function structure.
MD.verify(); //return the verify value and in this case return true coz both value is null.
var MD1 = new MyData(1,2); // intialized the value at the starting.
MD1.verify// return only the function structure.
MD1.verify(); // return false coz both value are not same.
MD1.verify(3,3);// return false coz this will not check this value intialized at the top
MyData.prototype.verify = function (foo,bar) {
return this.foo === this.bar;
};
var MD1 = new MyData(1,2);
MD1.verify();
MD1.verify(3,3);// return false coz this keyword used with foo and bar that will check parent data
Ответ 8
Вам нужен отдельный экземпляр объекта для страницы - Literal.
Вы хотите просто передать данные, подобные объектам DTO, просто GET SET: - Literal
Вы хотите создать реальные объекты с помощью поведения метода, несколько экземпляров - функцию конструктора, следовать принципам ООП, наследование: - функции конструктора.
Ниже приведено видео youtube, в котором подробно объясняется, что такое буквальный, какие функции-конструкторы и как они отличаются друг от друга.
Ответ 9
Как упоминалось в https://www.w3schools.com/js/js_object_definition.asp
Используя литерал объекта, вы define и создаете, один объект одинутверждение.
Также
Литерал объекта создает только один объект. Иногда нам нравится тип объекта, который можно использовать для создания объектов many одного типа.