На уровне приложения вы обычно хотите иметь один репозиторий на агрегат. Мотивация заключается в том, что вы пытаетесь свести к минимуму объем кода, который связан с деталями вашей реализации.
См. Парнас, 1972 .
Таким образом, в коде клиента этот стиль предпочтителен:
PaperBag paperBag = paperBagsRepository.get(paperBagId);
PlasticBag plasticBag = plasticBagsRepository.get(plasticBagId);
У вас есть , чтобы сделать это таким образом? Нет. Ни Парнас, ни Полиция DDD не пойдут, чтобы пнуть вашу дверь. Но их разделение облегчает изменение кода , что является важным свойством для устойчивого успеха.
Ваше понимание является неправильным:
myFunction().myProperty; // myFunction has no properties
Причина это не работает, состоит в том, потому что ".myProperty" применяется к возвращенному значению "myFunction ()", не к объекту "myFunction". К остроумию:
$ js
js> function a() { this.b=1;return {b: 2};}
js> a().b
2
js>
Помните, "()" оператор. "myFunction" не является тем же как "myFunction ()". Вам не нужен "возврат" когда instanciang с новым:
js> function a() { this.b=1;}
js> d = new a();
[object Object]
js> d.b;
1
Для ответа на конкретный вопрос технически функции всегда являются объектами.
Например, можно всегда делать это:
function foo(){
return 0;
}
foo.bar = 1;
alert(foo.bar); // shows "1"
Функции JavaScript ведут себя несколько как классы на других языках ООП, когда они используют this
указатель. Они можно инстанцировать как объекты с новым ключевым словом:
function Foo(){
this.bar = 1;
}
var foo = new Foo();
alert(foo.bar); // shows "1"
Теперь это отображение от других языков ООП до JavaScript перестанет работать быстро. Например, нет на самом деле никакой такой вещи как классы в JavaScript - объекты используют опытную цепочку для наследования вместо этого.
если Вы собираетесь сделать какой-либо вид значительного программирования в JavaScript, я настоятельно рекомендую JavaScript: Хорошие Части Crockford, тем парнем Вы послали по электронной почте.
"Глобальный" объем JavaScript (по крайней мере, в браузере) window
объект.
Это означает это, когда Вы делаете this.myProperty = "foo"
и вызовите функцию как плоскость myFunction()
Вы на самом деле устанавливаете window.myProperty = "foo"
Вторая точка с myFunction().myProperty
это здесь, Вы смотрите на возвращаемое значение myFunction()
, настолько естественно, который не будет иметь никаких свойств, поскольку это возвращает пустой указатель.
То, о чем Вы думаете, является этим:
function myFunction()
{
myFunction.myProperty = "foo";
}
myFunction();
alert(myFunction.myProperty); // Alerts foo as expected
Это - (почти) то же как
var myFunction = new Function('myFunction.myProperty = "foo";');
myFunction();
Когда Вы используете его в new
контекст, затем "возвращаемое значение" является Вашим новым объектом, и "этот" указатель изменяется, чтобы быть Вашим новым объектом, таким образом, это работает, как Вы ожидаете.
Нет ничего волшебного о функциях и конструкторах. Все объекты в JavaScript являются … хорошо, объектами. Но некоторые объекты являются более особенными, чем другие: а именно, встроенные объекты. Различие заключается главным образом в следующих аспектах:
null
и undefined
специальные объекты. Любая попытка использовать метод на этих объектах или определить новые методы вызывает исключение.+
, -
, *
, /
.+
.()
, и new
оператор. У последнего есть врожденное знание о том, как использовать prototype
свойство конструктора, создайте объект с надлежащими внутренними ссылками к прототипу и назовите функцию конструктора на нем установкой this
правильно.При изучении стандарта ECMAScript (PDF), Вы будете видеть, что все они, "дополнительная" функциональность определяется как методы и свойства, но многие из них не доступны программистам непосредственно. Некоторые из них будут выставлены в новом пересмотре стандартного ES3.1 (проект с 15 декабря 2008: PDF). Одно свойство (__proto__
) уже выставляется в Firefox.
Теперь мы можем ответить на Ваш вопрос непосредственно. Да, функциональный объект имеет свойства, и мы можем добавить/удалить их по желанию:
var fun = function(){/* ... */};
fun.foo = 2;
console.log(fun.foo); // 2
fun.bar = "Ha!";
console.log(fun.bar); // Ha!
Действительно не имеет значения, что на самом деле делает функция — это никогда не приходит к игре, потому что мы не называем его! Теперь давайте определим его:
fun = function(){ this.life = 42; };
Отдельно это не конструктор, это - функция, которая воздействует на ее контекст. И мы можем легко обеспечить его:
var context = {ford: "perfect"};
// now let's call our function on our context
fun.call(context);
// it didn't create new object, it modified the context:
console.log(context.ford); // perfect
console.log(context.life); // 42
console.log(context instanceof fun); // false
Поскольку Вы видите, что это добавило еще одно свойство к уже существующему объекту.
Для использования нашей функции в качестве конструктора, мы должны использовать new
оператор:
var baz = new fun();
// new empty object was created, and fun() was executed on it:
console.log(baz.life); // 42
console.log(baz instanceof fun); // true
Как видете new
сделанный нашей функцией конструктор. Следующие действия были сделаны new
:
{}
) был создан.fun.prototype
. В нашем случае это будет пустой объект ({}
) потому что мы не изменили его всегда.fun()
был назван с этим новым объектом как контекст.Это до нашей функции для изменения нового объекта. Обычно это настраивает свойства объекта, но это может сделать то, что это любит.
Забавные мелочи:
Поскольку конструктор является просто объектом, мы можем вычислить его:
var A = function(val){ this.a = val; };
var B = function(val){ this.b = val; };
var C = function(flag){ return flag ? A : B; };
// now let's create an object:
var x = new (C(true))(42);
// what kind of object is that?
console.log(x instanceof C); // false
console.log(x instanceof B); // false
console.log(x instanceof A); // true
// it is of A
// let's inspect it
console.log(x.a); // 42
console.log(x.b); // undefined
// now let's create another object:
var y = new (C(false))(33);
// what kind of object is that?
console.log(y instanceof C); // false
console.log(y instanceof B); // true
console.log(y instanceof A); // false
// it is of B
// let's inspect it
console.log(y.a); // undefined
console.log(y.b); // 33
// cool, heh?
Конструктор может возвратить значение, переопределяющее недавно созданный объект:
var A = function(flag){
if(flag){
// let's return something completely different
return {ford: "perfect"};
}
// let's modify the object
this.life = 42;
};
// now let's create two objects:
var x = new A(false);
var y = new A(true);
// let's inspect x
console.log(x instanceof A); // true
console.log(x.ford); // undefined
console.log(x.life); // 42
// let's inspect y
console.log(y instanceof A); // false
console.log(y.ford); // perfect
console.log(y.life); // undefined
Как видете x
имеет A
с прототипом и всеми, в то время как y
наш "явный" объект, который мы возвратили от конструктора.
Действительно, Функции являются 'гражданами первого класса': они - Объект.
Каждый объект имеет Прототип, но только на прототип функции можно сослаться непосредственно. Когда new
назван с функциональным объектом как аргумент, новый объект создается с помощью прототипа функционального объекта в качестве прототипа, и this
установлен на новый объект, прежде чем функция будет введена.
Таким образом, Вы могли вызвать каждую функцию Конструктор, даже если она уезжает this
один.
Существуют очень хорошие учебные руководства там на конструкторах, прототипы и т.д. Лично, я узнал о много из Объектно-ориентированного программирования в JavaScript. Это показывает эквивалентность функции, которая 'наследовала' ее прототип, но использование this
для заполнения свойств нового объекта и функционального объекта, который использует определенный прототип:
function newA() { this.prop1 = "one"; } // constructs a function object called newA
function newA_Too() {} // constructs a function object called newA_Too
newA_Too.prototype.prop1 = "one";
var A1 = new newA();
var A2 = new newA_Too();
// here A1 equals A2.
Во-первых, JavaScript не ведет себя тот же путь об объектах, как C++ / Java делает, таким образом, необходимо бросить те виды идей из окна, чтобы смочь понять, как JavaScript работает.
Когда эта строка выполняется:
var myFunctionVar = new myFunction();
затем this
в myFunction()
относится к этому новому объекту, который Вы создаете - myFunctionVar
. Таким образом эта строка кода:
this.myProperty = "Am I an object!";
по существу имеет результат
myFunctionVar.myProperty = "Am I an object!";
Это могло бы помочь Вам смотреть на некоторую документацию относительно new
оператор. В JS, new
оператор по существу позволяет Вам создавать объект из функции - любая простая функция. Нет ничего специального о функции, которую Вы используете с new
оператор, который отмечает его как конструктора, как это было бы в C++ или Java. Поскольку в документации говорится:
Создание пользовательского типа объекта требует двух шагов:
- Определите тип объекта путем записи функции.
- Создайте экземпляр объекта с новым.
Таким образом, что Вы сделали с кодом
function myFunction(){
this.myProperty = "Am I an object!";
}
должен создать функцию, которая была бы полезна как конструктор. Причина, почему код myFunction.myProperty
сбои - то, что нет никакой названной ссылки myFunction
.
JavaScript основан на сценарии ECMA. Его спецификация использует модель разработки прототипа для него, чтобы быть ООП. Как никогда, сценарий ECMA не осуществляет строгие типы данных. Объект нужно инстанцировать по той же причине, что сценарий ECMA требует 'нового' вызова, который выделит память для свойства, Иначе это останется функцией, и можно назвать его, если Вам нравится, в этом случае, то свойство инициализирует и затем будет уничтожено, когда функция закончится.
Только то, когда Вы инстанцируете с новым ключевым словом, совершает функциональный поступок как конструктора.
Результатом является объект, который может использовать "это" ключевое слово для доступа к свойствам элемента. Это ключевое слово в методе не имеет никакого смысла, когда функция используется любой другой путь.