今天我想知道angularjs的一些奇怪行为。我使用console.log来记录$ scope,没有键附加到名为val1的作用域,但当我使用console.log($scope.val1)
作为对象返回值时。在挖掘出原因之后,我发现它正在访问父范围,因为在$ scope中没有名为val1的kay。现在我的问题是,
哪种做法很好?你能证明合理吗?
$scope.$parent.val1
$scope.val1
答案 0 :(得分:4)
您通常不应该使用$scope.$parent
而是依赖于Javascripts原型继承。通过直接访问父级,如果您在范围层次结构中向上移动指令/控制器,则会冒着代码中断的风险,而数据现在位于$scope.$parent.$parent
上。
相反,永远不要直接在作用域上写入属性,而是写入作用域对象上的对象。
说你做:
$scope.$parent.value = 'x';
然后你做:
console.log($scope.value);
这会将x
打印到控制台。如果你这样做:
$scope.value = 'y';
您不是在父作用域上修改value
属性,而是在子作用域上引入新属性。因此$scope.$parent.value
仍将包含x
。
要解决这个问题,你可以:
$scope.$parent.data = {value: 'x'};
console.log($scope.data.value); // prints x
$scope.data.value = 'y';
console.log($scope.data.value); // prints y
console.log($scope.$parent.data.value); // also prints y
这样做的原因是,它不是在子作用域上创建新的value
属性,而是首先需要查找data
属性。并且这不在子范围上,因此它会在原型链($ parent)上找到data
对象。在父项上找到data
对象,而在该对象上设置value
属性。
答案 1 :(得分:1)
这取决于val1
的类型,如果它是原语,则必须通过$ scope。$ parent显式访问它。
如果它是一个对象,你可以利用Angular中父和子范围之间存在的原型继承,并且只是定期引用它,因为我相信你知道,对象是通过引用传递的,所以对它的任何改变都是对象将在父范围内更改它。