簡體   English   中英

保持觀察者的角度? (ng-repeat POV)

[英]Conserving watchers in angular ? (ng-repeat POV)

我已經知道如何處理ng-repeat性能問題的常見模式(與觀察者一起),如: one-time-bindinfinite scroll etc

但我看到一個人的答案建議轉向指令。

好的,我開始采用簡單的舊方法

方法#1的plunker:

這個html有100個項目:

  <div ng-repeat="e in ct.arr">
      <div class='s'> 
        <span >name:{{e.name}} , age:{{e.age}} , height:{{e.height}}</span>
      <hr>
  </div>

這將產生301觀察者,當我點擊一個按鈕時我可以更改第5'th項目:

在此輸入圖像描述

那么我想把它移到指令(就像建議的那樣):

方法#2的掠奪者

現在HTML是:

 <div ng-repeat="e in ct.arr">
     <div class='s'> 
        <span  my-event="e" ></span>
      <hr>
    </div>
  </div>

指令:

.directive('myEvent', function() {
  return {
    scope: {
      event: "=myEvent"
    },
    link: link,
   }

  function link(scope, element, attrs) {
     var ev = scope.event;
     element.text('name:'+ev.name +', age:'+ev.age+' , height:'+ev.height)
  }
});

現在我只有101觀察者,但現在按鈕沒有影響:

在此輸入圖像描述

問題:

  1. 如果我是對的,100名觀察者是因為孤立范圍的直接別名是'=' 但如果它是該項目的直接別名,為什么我沒有看到按鈕點擊后的修改?

  2. 如果我想看到修改,我是否會遇到301觀察者? 還有什么我沒有想到的 - 可以做到嗎?

像Alainlb寫的那樣,你只是在創建時計算內容一次。 當然就像你在評論中寫一樣,使用template :'<span>name:{{event.name}} ,age:{{event.age}} , height:{{event.height}} </span>'添加手表(每個{{ ... }}是幕后的手表)。

想到的第一個解決方案是使用監視指令的項目。 深度監視具體,以便它可以檢測對象屬性的更改,而不僅僅是對實際對象引用的更改:

function link(scope, element, attrs) {
    scope.$watch('event', function(ev) {
        element.text('name:' + ev.name + ', age:' + ev.age + ' , height:' + ev.height);
    }, true);
}

http://plnkr.co/edit/marpxMx5qin7mOlFwp3X?p=preview

分數:201手表

但我們可以做得更好; 因為我們正在手動觀察,所以= scope綁定現在是多余的。 哦,然后scope: {}配置為空; 我們甚至可以沒有范圍,既不是孤立的,也不是新的原型繼承的。 讓我們使用scope: false (每次迭代可以節省1個范圍對象,對於許多迭代來說都是很好的增益)。

我們現在直接觀察my-event屬性中給出的表達式:

.directive('myEvent', function() {
    return {
        scope: false,
        link: link,
    };

    function link(scope, element, attrs) {
        scope.$watch(
            attrs.myEvent,
            function(ev) {
                element.text('name:' + ev.name + ', age:' + ev.age + ' , height:' + ev.height);
            },
            true
        );
    }
});

http://plnkr.co/edit/lvnIQCJMnniFlOeRseaZ?p=preview

分數:101手表


有一個問題:深度觀察產生較少的手表,但它們更昂貴,因為它們迭代觀察對象的每個屬性。 因此,真正的性能提升可能會低於它看起來的效果 - 101手表對301手表。 我們可以做得更好嗎?

在嘗試之前,我首先要測量101深表和301表之間的真正性能差異。 如果可以忽略不計,我們沒關系。 否則,我們可能會使用Javascript屬性getter和setter在我們的更新中變得“更聰明”,並且可能在對象上手動設置臟標志。 這將很復雜。

更好的方法是永遠不要改變對象的內部屬性(將其視為不可變 - 一般來說是一個好主意)並更改引用本身。 即:

vm.c10 = function (){
    this.arr[4] = {
        name: "aaaa",
        age: "aaaa",
        height: "aaaa"
    };
};

然后你不再需要深入觀察(從scope.$watch的參數中刪除, true scope.$watch )。 如果你可以強制執行對象是不可變的約定( Immutable.js anybody?),你是獨自工作,或者團隊(現在和將來)對這個約定有良好的溝通和理解,那么這種方法效果最好。 否則就會出現邪惡的錯誤。

這是因為你使用鏈接,編譯指令的html一次並顯示它

試試這個http://plnkr.co/edit/spYF935i5TIX9HApVTF4?p=preview

.directive('myEvent', function() {
  return {
    scope: {
      event: "=myEvent"
    }
    , template :'<span>name:{{event.name}}  ,age:{{event.age}} , height:{{event.height}} </span>'
   }

});

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM