gpt4 book ai didi

javascript - AngularJS ng-repeat 很慢

转载 作者:行者123 更新时间:2023-12-04 15:07:24 26 4
gpt4 key购买 nike

渲染很多条目并不慢。问题是每当 $scope.data得到更新,它首先在元素的末尾添加新项目,然后在匹配新的 $scope.data 时减少它。 .

例如:

<div class="list" ng-repeat="entry in data">
<h3>{{entry.title}}</h3>
</div>

此脚本正在更新 $scope.data :

$scope.load = function() {
$scope.data = getDataFromDB();
}

假设我在 $scope.data 中有 5 个条目.条目是:

[
{
id: 1,
title: 1
},
{
id: 2,
title: 2
},
......
]

$scope.data已经有这些条目然后被重新加载(调用 $scope.data = getDataFromDB();),大约 0.1s - 0.2s 的 DOM 元素有 10 个元素(重复元素),然后在 0.1s - 0.2s 之后它减少到 5。

所以问题是更新 ng-repeat DOM 时有大约 0.1s - 0.2s 的延迟。当我实现实时搜索时,这看起来真的很糟糕。每当它从数据库更新时,ng-repeat DOM 元素每次都会在短暂的毫秒内添加。

如何使渲染变得即时?


已编辑

我会在这里粘贴我所有的代码:

Controller :

$scope.search = function (table) {
$scope.currentPage = 1;
$scope.endOfPage = false;
$scope.viewModels = [];
$scope.loadViewModels($scope.orderBy, table);
}

$scope.loadViewModels = function (orderBy, table, cb) {
if (!$scope.endOfPage) {
let searchKey = $scope.page.searchString;
let skip = ($scope.currentPage - 1) * $scope.itemsPerPage;
let searchClause = '';

if (searchKey && searchKey.length > 0) {
let searchArr = [];
$($scope.vmKeys).each((i, key) => {
searchArr.push(key + ` LIKE '%` + searchKey + `%'`);
});
searchClause = `WHERE ` + searchArr.join(' OR ');
}

let sc = `SELECT * FROM ` + table + ` ` + searchClause + ` ` + orderBy +
` LIMIT ` + skip + `, ` + $scope.itemsPerPage;
sqlite.query(sc, rows => {
$scope.$apply(function () {
var data = [];
let loadedCount = 0;
if (rows != null) {
$scope.currentPage += 1;
loadedCount = rows.length;
if (rows.length < $scope.itemsPerPage)
$scope.endOfPage = true

for (var i = 0; i < rows.length; i++) {
let item = rows.item(i);
let returnObject = {};
$($scope.vmKeys).each((i, key) => {
returnObject[key] = item[key];
});
data.push(returnObject);
}
$scope.viewModels = $scope.viewModels.concat(data);
}
else
$scope.endOfPage = true;

if (cb)
cb(loadedCount);
})
});
}
}

View :

<div id="pageContent" class="root-page" ng-controller="noteController" ng-cloak>
<div class="row note-list" ng-if="showList">
<h3>Notes</h3>
<input ng-model="page.searchString" id="search"
ng-keyup="search('notes')" type="text" class="form-control"
placeholder="Search Notes" style="margin-bottom:10px">
<div class="col-12 note-list-item"
ng-repeat="data in viewModels track by data.id"
ng-click="edit(data.id)"
ontouchstart="touchStart()" ontouchend="touchEnd()"
ontouchmove="touchMove()">
<p ng-class="deleteMode ? 'note-list-title w-80' : 'note-list-title'"
ng-bind-html="data.title"></p>
<p ng-class="deleteMode ? 'note-list-date w-80' : 'note-list-date'">{{data.dateCreated | displayDate}}</p>
<div ng-if="deleteMode" class="note-list-delete ease-in" ng-click="delete($event, data.id)">
<span class="btn fa fa-trash"></span>
</div>
</div>
<div ng-if="!deleteMode" ng-click="new()" class="add-btn btn btn-primary ease-in">
<span class="fa fa-plus"></span>
</div>
</div>
<div ng-if="!showList" class="ease-in">
<div>
<div ng-click="back()" class="btn btn-primary"><span class="fa fa-arrow-left"></span></div>
<div ng-disabled="!isDataChanged" ng-click="save()" class="btn btn-primary" style="float:right">
<span class="fa fa-check"></span>
</div>
</div>
<div contenteditable="true" class="note-title"
ng-bind-html="selected.title" id="title">
</div>
<div contenteditable="true" class="note-container" ng-bind-html="selected.note" id="note"></div>
</div>
</div>

<script src="../js/pages/note.js"></script>

从以下位置调用它:

$scope.loadViewModels($scope.orderBy, 'notes');

sqlite 查询:

query: function (query, cb) {
db.transaction(function (tx) {
tx.executeSql(query, [], function (tx, res) {
return cb(res.rows, null);
});
}, function (error) {
return cb(null, error.message);
}, function () {
//console.log('query ok');
});
},

它是apache cordova框架,所以在Android模拟器中使用webview。


我的代码结构

<html ng-app="app" ng-controller="pageController">
<head>....</head>
<body>
....
<div id="pageContent" class="root-page" ng-controller="noteController" ng-cloak>
....
</div>
</body>
</html>

所以 Controller 里面有 Controller 。 parent 是pageController child 是noteController .像这样的结构会减慢 ng-repeat 吗?指令?

顺便说一句,使用 track by没有帮助。渲染时仍然有延迟。我也可以修改条目,所以当条目更新时,它也应该在列表中更新。


注意

经过彻底调查,发现了一些奇怪的事情。通常 ng-repeat 项目有 hash键入它。在我的例子中,ng-repeat items 没有它。这是问题的原因吗?

最佳答案

提高性能的一种方法是在 ng-repeat 表达式中使用 track by 子句:

<div class="list" ng-repeat="entry in data track by entry.id">
<h3>{{entry.title}}</h3>
</div>

来自文档:

Best Practice: If you are working with objects that have a unique identifier property, you should track by this identifier instead of the object instance, e.g. item in items track by item.id. Should you reload your data later, ngRepeat will not have to rebuild the DOM elements for items it has already rendered, even if the JavaScript objects in the collection have been substituted for new ones. For large collections, this significantly improves rendering performance.

有关详细信息,请参阅

关于javascript - AngularJS ng-repeat 很慢,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/65871863/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com