我的团队想要转向一种依赖注入的风格,它更接近于用于Angular代码库的CommonJS / Node JS语法:
var myDependency = require('myDependency');
我已经开始在我的函数顶部直接使用$injector.get()
,到目前为止没有明显的麻烦。这意味着我已将此转换为:
angular.module('modD', ['modA', 'modB', 'modC'])
.service('serviceD', ['serviceA', 'serviceB', 'serviceC', function(serviceA, serviceB, serviceC) {
//My code here
}])
分为:
angular.module('modD', ['modA', 'modB', 'modC'])
.service('serviceD', ['$injector', function($injector) {
var serviceA = $injector.get('serviceA');
var serviceB = $injector.get('serviceB');
var serviceC = $injector.get('serviceC');
//My code here
}]);
我有什么遗失的东西。不在函数定义之外声明所需的依赖项会导致任何类型的性能问题吗?
答案 0 :(得分:1)
注意:此答案尚未经过测试。 在深入了解角度代码之后,我发现了这个:
style="@android:style/Widget.Holo.Light.RatingBar.Small
它的电话似乎是:
// in function createInjector
function provider(name, provider_) {
...
if (isFunction(provider_) || isArray(provider_)) {
provider_ = providerInjector.instantiate(provider_);
}
...
return providerCache[name + providerSuffix] = provider_;
}
...
function factory(name, factoryFn, enforce) {
return provider(name, {
$get: enforce !== false ? enforceReturnValue(name, factoryFn) : factoryFn
});
}
function service(name, constructor) {
return factory(name, ['$injector', function($injector) {
return $injector.instantiate(constructor);
}]);
}
...
// in function createInternalInjector
function invoke (...){
...
for (i = 0, length = $inject.length; i < length; i++) {
args.push(
locals && locals.hasOwnProperty(key)
? locals[key]
: getService(key, serviceName)
);
}
...
return fn.apply(self, args);
}
function instantiate(...){
...
var instance = Object.create((isArray(Type) ? Type[Type.length - 1] : Type).prototype || null);
var returnedValue = invoke(Type, instance, locals, serviceName);
return isObject(returnedValue) || isFunction(returnedValue) ? returnedValue : instance;
}
...
return {
invoke: invoke,
instantiate: instantiate,
get: getService,
annotate: createInjector.$$annotate,
has: function(name) {
return providerCache.hasOwnProperty(name + providerSuffix) || cache.hasOwnProperty(name);
}
};
已调用service
调用了factory
instantiate
已调用factory
调用了provider
所以我认为你的问题等于逐个调用$ injector.get()与调用$ injector.instantiate()一次具有相同的性能吗?
如代码所示,instantiate
调用了instantiate
,它为您注入的每个服务实际调用了invoke
。而getService
只是绑定到$injector.get
。
所以我的平等问题的答案是 True 。
你问题的答案是不,他们的表现非常接近。
如果我错了,请纠正我,谢谢!
答案 1 :(得分:1)
在服务的情况下,两段代码之间没有显着差异。 $injector.get(...)
电话不会提供任何开销。但它为每个依赖提供了大量额外的字符。
对于具有本地依赖关系的注入事项(控制器和路由/状态解析器),同样的事情会有所不同。
当这些依赖
app.controller('SomeCtrl', function ($scope, service) { ... });
替换为$injector.get(...)
,它会阻塞$scope
- 它是本地依赖项。并且,如此检索其他依赖项,控制器将失去其可测试性。无法使用
$controller('SomeCtrl', { service: mockedService });
我个人并不知道$injector.get(...)
如何对项目的风格有所帮助(而且还没有看到一个好的风格指南)。
节点使用require
函数,因为它适用于它,而不是因为它更好或更酷。另一种方法是将每个Node脚本打包成类似AMD的包装器,这将是痛苦的。幸运的是,我们已经有了围绕Angular单位的包装器!