Приветствую, читатель.
Сегодня я прочитал статью-перевод, которая меня слегка разочаровала. Во-первых, содержанием (нет, я не виню переводчика). Во-вторых, тем, что я не увидел тех трюков, которые я хотел бы увидеть.
Поэтому, хочу поделиться с вами теми возможностями $parse
, которые я знаю.
$scope.$eval
Если у вас есть вызов $scope.$eval
с одним и тем же выражением в цикле — однозначно меняйте на $parse
.
for (var i = 0; i < 1e5; ++i) {
$scope.$eval('my.expr'); // слоупок
}
var expr = $parse('my.expr');
for (var j = 0; j < 1e5; ++j) {
expr($scope); // флэш
}
$scope.$watch в директивах
Когда я узнал об этой технике, то моя челюсть устремилась к полу. Читаем комментарии к коду.
// slow example
app.directive('myDir', function() {
return {
link: function(scope, elem, attrs) {
// Медленно
scope.foo = scope.$eval(attrs.foo);
// Медленно
scope.$watchCollection(attrs.list, function(list) {
// Some code
});
}
};
});
// fast example
app.directive('myDir', function($parse) {
return {
compile: function(tElem, tAttrs) {
// compile вызывается один раз для элемента, в котором "вызов" директивы
var fooExpr = $parse(tAttrs.foo),
listExpr = $parse(tAttrs.list);
// а вот post-link для каждого элемента
return function postLinkFn(scope) {
// Однако $parse быстро получает значение
scope.foo = fooExpr(scope);
// Опять же, $parse хорошо выступает в качестве watchExpr
scope.$watchCollection(listExpr, function(list) {
// Some code
});
}
}
};
});
Последний трюк — использование $parse
в compile
функции директивы, с дальнейшим вызовом в link
. Очень хорошо сказывается на производительности.
Надеюсь, что приоткрыл для кого-то из вас завесу тайны, и теперь вы будете использовать сервис $parse
в благих целях.