Array.prototype.filter的猴子补丁破坏了AngularJS 1.6

时间:2019-03-21 15:17:20

标签: javascript arrays angularjs angularjs-directive angularjs-1.6

ngSwitchWhen引发错误“无法读取未定义的属性'NaN'”

我正在覆盖Array原型上的现有过滤器方法,这适用于angular 1.5.7版本。 最近,我将其升级到1.6.10。相同的代码无法正常工作,并且在浏览器控制台中引发错误Cannot read property 'NaN' of undefined

HTML

  <select ng-model="selection" ng-options="item for item in items">
  </select>
  <code>selection={{selection}}</code>
  <hr/>
  <div class="animate-switch-container"
    ng-switch on="selection">
      <div class="animate-switch" ng-switch-when="settings|options" ng-switch-when-separator="|">Settings Div</div>
      <div class="animate-switch" ng-switch-when="home">Home Span</div>
      <div class="animate-switch" ng-switch-default>default</div>
  </div>

控制器

 Array.prototype.filter = function (predicateFunction) {
   let results = [];
      this.forEach((item) => {
        if (predicateFunction(item)) {
          results.push(item);
        }
      });
    return results;
  };

  $scope.items = ['settings', 'home', 'options', 'other'];
  $scope.selection = $scope.items[0];

我在plunker中转载了此问题。

1 个答案:

答案 0 :(得分:0)

您的Array.prototype.filter猴子补丁存在缺陷:

 Array.prototype.filter = function (predicateFunction) {
   let results = [];
      ̶t̶h̶i̶s̶.̶f̶o̶r̶E̶a̶c̶h̶(̶(̶i̶t̶e̶m̶)̶ ̶=̶>̶ ̶{̶
      this.forEach((item,index,array) => {
        ̶i̶f̶ ̶(̶p̶r̶e̶d̶i̶c̶a̶t̶e̶F̶u̶n̶c̶t̶i̶o̶n̶(̶i̶t̶e̶m̶)̶)̶ ̶{̶
        if (predicateFunction(item,index,array)) {
          results.push(item);
        }
      });
    return results;
  };

应使用三个参数调用回调:

  • 元素的值
  • 元素的索引
  • 正在遍历的Array对象

更新

ES5标准建议使用这种polyfill:

if (!Array.prototype.filter){
  Array.prototype.filter = function(func, thisArg) {
    'use strict';
    if ( ! ((typeof func === 'Function' || typeof func === 'function') && this) )
        throw new TypeError();

    var len = this.length >>> 0,
        res = new Array(len), // preallocate array
        t = this, c = 0, i = -1;
    if (thisArg === undefined){
      while (++i !== len){
        // checks to see if the key was set
        if (i in this){
          if (func(t[i], i, t)){
            res[c++] = t[i];
          }
        }
      }
    }
    else{
      while (++i !== len){
        // checks to see if the key was set
        if (i in this){
          if (func.call(thisArg, t[i], i, t)){
            res[c++] = t[i];
          }
        }
      }
    }

    res.length = c; // shrink down array to proper size
    return res;
  };
}

有关更多信息,请参见MDN JavaScript Reference - Array.prototype.filter polyfill