请耐心听我说。我知道还有其他答案,比如:
AngularJS:服务vs提供商vs工厂
然而,我仍然不知道你什么时候会使用服务而不是工厂。
据我所知,factory通常用于创建可以被多个控制器调用的“通用”函数:创建通用控制器函数
比起服务,Angular文档似乎更喜欢工厂。他们甚至在使用工厂时提到“服务”,这更令人困惑!http://docs.angularjs.org/guide/dev_guide.services.creating_services
那么什么时候使用服务呢?
是否有一些事情只有通过服务才能做到或更容易做到?
幕后有什么不同吗?性能/内存差异呢?
举个例子。除了声明的方法,它们看起来是一样的,我不明白为什么我要做一个而不是另一个。http://jsfiddle.net/uEpkE/
更新:从Thomas的回答中,似乎暗示服务是为了更简单的逻辑,而工厂是为了更复杂的逻辑和私有方法,所以我更新了下面的小提琴代码,似乎两者都能支持私有函数?
myApp.factory('fooFactory', function() {
var fooVar;
var addHi = function(foo){ fooVar = 'Hi '+foo; }
return {
setFoobar: function(foo){
addHi(foo);
},
getFoobar:function(){
return fooVar;
}
};
});
myApp.service('fooService', function() {
var fooVar;
var addHi = function(foo){ fooVar = 'Hi '+foo;}
this.setFoobar = function(foo){
addHi(foo);
}
this.getFoobar = function(){
return fooVar;
}
});
function MyCtrl($scope, fooService, fooFactory) {
fooFactory.setFoobar("fooFactory");
fooService.setFoobar("fooService");
//foobars = "Hi fooFactory, Hi fooService"
$scope.foobars = [
fooFactory.getFoobar(),
fooService.getFoobar()
];
}
与服务相比,没有什么是工厂做不到或做得更好的。反之亦然。工厂似乎更受欢迎。这样做的原因是方便处理私人/公共成员。在这方面,服务将更加笨拙。
在编码Service时,你倾向于通过“this”关键字将对象成员设为public,然后可能突然发现那些public成员对于私有方法(即内部函数)是不可见的。
var Service = function(){
//public
this.age = 13;
//private
function getAge(){
return this.age; //private does not see public
}
console.log("age: " + getAge());
};
var s = new Service(); //prints 'age: undefined'
Angular使用" new "关键字为你创建一个服务,所以Angular传递给控制器的实例也会有同样的缺点。
当然你可以用this/that来解决这个问题:
var Service = function(){
var that = this;
//public
this.age = 13;
//private
function getAge(){
return that.age;
}
console.log("age: " + getAge());
};
var s = new Service();// prints 'age: 13'
但是对于一个大的服务常量this\that-ing会使代码可读性很差。
此外,服务原型不会有private成员,只有public成员可以使用:
var Service = function(){
var name = "George";
};
Service.prototype.getName = function(){
return this.name; //will not see a private member
};
var s = new Service();
console.log("name: " + s.getName());//prints 'name: undefined'
综上所述,使用Factory更加方便。As Factory没有这些缺点。我建议在默认情况下使用它。
解释
这里有不同的东西:
第一:
如果你使用一个服务,你将得到一个函数的实例("this")
关键字)。
如果您使用工厂,您将获得返回的值
调用函数引用(工厂中的return语句)。
裁判:角。Service vs angular.factory
第二:
记住,AngularJS中的所有提供者(value, constant, services, factories)都是单例的!
第三:
使用一种或另一种(服务或工厂)取决于代码风格。
但是,AngularJS中常用的方法是使用工厂。
为什么?
因为“工厂方法是将对象导入AngularJS依赖注入系统的最常用方法。它非常灵活,可以包含复杂的创建逻辑。由于工厂是常规函数,我们还可以利用新的词法作用域来模拟“私有”变量。这非常有用,因为我们可以隐藏给定服务的实现细节。”
(参考:http://www.amazon.com/Mastering-Web-Application-Development-AngularJS/dp/1782161821)。
使用
Service:可以通过将()附加到注入的函数引用来共享有用的实用程序函数。也可以使用injectedArg.call(this)或类似的方法运行。
Factory:可能用于返回一个' class '函数,然后可以重新创建实例。
因此,当您的服务中有复杂的逻辑而又不想暴露这种复杂性时,请使用工厂。
在其他情况下,如果你想返回一个服务的实例,只需使用service。
但是随着时间的推移你会发现80%的情况下你会用到工厂。
详情请访问:http://blog.manishchhabra.com/2013/09/angularjs-service-vs-factory-with-example/
更新:
这里有很棒的帖子:
http://iffycan.blogspot.com.ar/2013/05/angular-service-or-factory.html
如果你想让你的函数像普通函数一样被调用,请使用
工厂。如果你想要你的函数用new
接线员,使用服务。如果你不知道其中的区别,就用factory。”
更新:
AngularJS团队做了他的工作并给出了解释:
http://docs.angularjs.org/guide/providers
从这一页开始:
“工厂和服务是最常用的食谱。它们之间唯一的区别是Service recipe更好地用于自定义类型的对象,而Factory可以生成JavaScript原语和函数。”
可以使用你想要的方式:是否创建对象或只是从两者访问函数
您可以从服务中创建新对象
app.service('carservice', function() {
this.model = function(){
this.name = Math.random(22222);
this.price = 1000;
this.colour = 'green';
this.manufacturer = 'bmw';
}
});
.controller('carcontroller', function ($scope,carservice) {
$scope = new carservice.model();
})
注意:
服务默认返回对象而不是构造函数。
这就是构造函数函数被设为这个的原因。模型属性。
由于此服务将返回对象,但是但是对象内部将是用于创建新对象的构造函数;
您可以从工厂创建新对象
app.factory('carfactory', function() {
var model = function(){
this.name = Math.random(22222);
this.price = 1000;
this.colour = 'green';
this.manufacturer = 'bmw';
}
return model;
});
.controller('carcontroller', function ($scope,carfactory) {
$scope = new carfactory();
})
注意:
Factory默认返回构造函数函数而不是对象。
这就是为什么new object可以用构造函数function创建。
创建只访问简单功能的服务
app.service('carservice', function () {
this.createCar = function () {
console.log('createCar');
};
this.deleteCar = function () {
console.log('deleteCar');
};
});
.controller('MyService', function ($scope,carservice) {
carservice.createCar()
})
创建用于访问简单函数的工厂
app.factory('carfactory', function () {
var obj = {}
obj.createCar = function () {
console.log('createCar');
};
obj.deleteCar = function () {
console.log('deleteCar');
};
});
.controller('MyService', function ($scope,carfactory) {
carfactory.createCar()
})
结论:
您可以使用您想要的方式,无论是创建新对象或
只是为了访问简单的函数
使用其中一种而不是另一种,不会对性能造成任何影响
两者都是单例对象,每个应用程序只创建一个实例。
在每个传递引用的地方都只有一个实例。
在angular文档中,工厂被称为服务,服务也被称为服务。