Подтвердить что ты не робот

Ng-repeat с несколькими фильтрами на большом наборе данных

Я все еще новичок в AngularJS, поэтому я просто пытаюсь сделать простое приложение CRUD. В настоящее время я вытаскиваю данные (в файле JSON) с $http в div, обрабатываемом контроллером MyCtrl1.

function MyCtrl1($scope, $http) {
    $http.get('data/accounts.json').success(function(data) {
        $scope.accounts = data;
    ...
    }); 
}

Внутри этого div есть table со следующим tbody:

<tbody>
    <tr ng-repeat="account in accounts | orderBy:sort.field:sort.desc | startFrom:currentPage * pageSize | limitTo:pageSize">
        <td contentEditable="true" ng-repeat="(label, value) in account" ng-show="fields[label].visible">{{value}}</td>
    </tr>
</tbody>

Фильтр orderBy сортируется в соответствии с выбранным полем; startFrom срезает массив, чтобы начать с определенной точки; limitTo фильтрует в соответствии с заданным размером страницы. Без фильтров разбиения на страницы производительность была довольно ужасной, но мне было интересно, есть ли альтернативный способ сделать это?

У меня есть Batarang для Chrome, а на вкладке Performance он показал ngRepeatWatch больше времени, и я считаю, что это связано со всей фильтрацией, которую я делаю.

4b9b3361

Ответ 1

{{выражение | фильтр1 | filter2}}

Просто используйте

<tr ng-repeat="account in accounts | filter1 | filter2 | filter3" >
  <td contentEditable="true" ng-repeat="(label, value) in account" ng-show="fields[label].visible">{{value}}</td>
</tr>

Angular 2 использует pipes, но он выглядит как фильтры:

<div>The chained hero birthday is
<p>{{  birthday | date:'fullDate' | uppercase}}</p>
<div>

Ответ 2

Я знаю, что этот вопрос старый, но для любого в будущем. Фильтрация в строке дорогостоящая (вычислительная), потому что она работает непосредственно на DOM, если вы имеете дело с большими объемами данных, 1000+ строк, гораздо лучше отфильтровать вашу коллекцию в контроллере, а затем повторить на этом.

Ответ 3

Я бы обрабатывал разбиение на страницы в контроллере или на стороне сервера. Я предполагаю, что ng-repeat просматривает весь ваш список, а не только то, что ему нужно наблюдать, что будет очень медленным.

Ответ 4

Это не фильтр, но вы можете использовать директиву ng-hide, оценивая индекс $для массива следующим образом:

<div class="col-sm-12 col-lg-12" ng-repeat="message in messages | orderBy: '-id' as filtered_result track by message.id  ">
  <div class="card-box widget-user" ng-hide="{{$index >= 4}}">
    <div>
      <img ng-src="{{message.imageUrl}}" class="img-responsive" alt="{{message.imageUrl}}">
      <div class="wid-u-info">
        <h3 class="m-t-0 m-b-5">{{message.title }}</h3>
        <p class="text-muted m-b-5 font-13" ng-bind-html="message.content | ellipsis:147 | trusted"></p>
        <!-- <p class="text-muted m-b-5 font-13">{{message.content | limitTo:130}}</p> -->
        <small class="label" ng-class="{'label-success':message.type=='Message','label-warning':message.type=='Announcement'}"><b>{{message.type}}</b></small>
      </div>
    </div>
  </div>
</div>

Ответ 5

CRUD следует обрабатывать в factory или службе, а не в контроллере. Я понимаю, что контроллер несет ответственность только за связь между представлениями и услугами.

Изменить 1: выдержка из руководства по стилю Джона Папа (Angular -1) - Отложить логику в контроллере, делегируя сервисам и фабрикам.

Почему?: Логика может быть повторно использована несколькими контроллерами при размещении внутри службы и открыта с помощью функции.

Почему?: Логика в сервисе проще изолировать в unit test, в то время как логику вызова в контроллере можно легко высмеять.

Почему?: Удаляет зависимости и скрывает детали реализации от контроллера.

Почему?: Сохраняет контроллер тонким, аккуратным и сфокусированным.

https://github.com/johnpapa/angular-styleguide/blob/master/a1/README.md#style-y035