微信小程序:setData 数据传输长度为 1678 KB,存在有性能问题

本文探讨了微信小程序中遇到的setData数据传输长度限制问题,提出通过分页加载和设置指定位置元素值来优化。此外,还强调了setData的使用注意事项,包括避免频繁调用、传递大量数据和后台态页面使用。同时,提到了图片资源管理,尤其是大图片和长列表图片可能引发的性能问题,建议减少大图片使用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

微信小程序:setData 数据传输长度为 1678 KB,存在有性能问题!
记录遇到的问题
本文也参考了其他文章

由于data 数据过大,比如 base64 / 数据列表返回内容过大,导致无法执行 setData功能。
这是因为setData设置的数据量是有限制的,单次设置的数据大小不得超过1024kb,否则就会出现如上错误。

问题做法:

data:{
  // 数据源
  list:[]
},

getListData:function(){
  // 本次加载的数据
  let _list = [];
  ...
  setData({
       // 将之前的数据与本次加载的数据合并后,一起提交
       list: this.data.list.concat(_list)
  });
}

改进后的做法:分页加载后,通过设置 list 指定位置的元素值,实现只提交新加载的数据,

data:{
  // 当前页数
  pageNo:0,
  // 数据源
  list:[]
},

getListData:function(){
  // 本次加载的数据
  let _list = [];
  ...
  setData({
       ['list[' + pageNo + ']']: _list,
  });
}

注意:改进后方案中的 list 与常规方案中的 list 已经不是同种数组。

常规方案中的 list,是一维数组,直接存放 item,结构为:[{…},{…},{…},…]。

而改进方案中的 list 是二维数组,每个子元素为一页 item 数据的集合,而子元素数组中的每个元素才是 item 数据,结构为:[[{…},{…},{…}],[{…},{…},{…}],[{…},{…},{…}],…],所以需要注意对wxml中的列表结构进行修改。

==================
来看看 setData 是什么

setData 函数用于将数据从逻辑层发送到视图层(异步),同时改变对应的 this.data 的值(同步)
Object 以 key: value 的形式表示,将 this.data 中的 key 对应的值改变成 value。
其中 key 可以以数据路径的形式给出,支持改变数组中的某一项或对象的某个属性,

注意:


1、直接修改this.data,而不调用this.setData(),是无法改变当前页面的状态的,会导致数据不一致/
2、仅支持可以JSON化的数据
3、单次设置的数据不能超过1024KB,尽量避免一次设置过多的数据/
4、不要把data中的任何一项的value设为undefined,否则这一项将不能被设置,可能会有潜在的问题

工作原理

小程序的视图层目前使用 WebView 作为渲染载体,而逻辑层是由独立的 JavascriptCore 作为运行环境。在架构上,WebView 和 JavascriptCore 都是独立的模块,并不具备数据直接共享的通道。当前,视图层和逻辑层的数据传输,实际上通过两边提供的 evaluateJavascript 所实现。即用户传输的数据,需要将其转换为字符串形式传递,同时把转换后的数据内容拼接成一份 JS 脚本,再通过执行 JS 脚本的形式传递到两边独立环境。

而 evaluateJavascript 的执行会受很多方面的影响,数据到达视图层并不是实时的。

常见的 setData 操作错误

1. 频繁的去 setData

在我们分析过的一些案例里,部分小程序会非常频繁(毫秒级)的去setData,其导致了两个后果:

Android 下用户在滑动时会感觉到卡顿,操作反馈延迟严重,因为 JS 线程一直在编译执行渲染,未能及时将用户操作事件传递到逻辑层,逻辑层亦无法及时将操作处理结果及时传递到视图层;
渲染有出现延时,由于 WebView 的 JS 线程一直处于忙碌状态,逻辑层到页面层的通信耗时上升,视图层收到的数据消息时距离发出时间已经过去了几百毫秒,渲染的结果并不实时;

2. 每次 setData 都传递大量新数据

由setData的底层实现可知,我们的数据传输实际是一次 evaluateJavascript 脚本过程,当数据量过大时会增加脚本的编译执行时间,占用 WebView JS 线程,

3. 后台态页面进行 setData

当页面进入后台态(用户不可见),不应该继续去进行setData,后台态页面的渲染用户是无法感受的,另外后台态页面去setData也会抢占前台页面的执行。

图片资源

目前图片资源的主要性能问题在于大图片和长列表图片上,这两种情况都有可能导致 iOS 客户端内存占用上升,从而触发系统回收小程序页面。

图片对内存的影响

在 iOS 上,小程序的页面是由多个 WKWebView 组成的,在系统内存紧张时,会回收掉一部分 WKWebView。从过去我们分析的案例来看,大图片和长列表图片的使用会引起 WKWebView 的回收。

图片对页面切换的影响

除了内存问题外,大图片也会造成页面切换的卡顿。我们分析过的案例中,有一部分小程序会在页面中引用大图片,在页面后退切换中会出现掉帧卡顿的情况。

当前我们建议开发者尽量减少使用大图片资源。

参考:https://blog.csdn.net/qq_38595560/article/details/81565925
https://zhuanlan.zhihu.com/p/181485977
————————————————
版权声明:本文为CSDN博主「拈花醉。」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/weixin_52541520/article/details/115215702

如果你试过其他博文的方法都不行的话,你看看你wxml绑定的办法中是否有用到类似的传参方式:

<view bindtap="test(JSON.stringify({index:index,list:list}))"></view>
1
我是通过uni-app编译成的小程序,写法如下

<view>@tap="test(JSON.stringify({index:index,list:list}))"</view>
1
其中list是数据列表,index是遍历list的index,这种传参方式就会导致setData 传输过大告警,解决方法是使用data-的形式传参

<view bindtap="test" data-index="{{index}}" data-list="{{list}}"></view>
1
特意试了很多其他写法,比如不传index,只传单独的list、将变量index换成其他变量、不使用JSON.stringify()等操作都不会出现警告
————————————————
版权声明:本文为CSDN博主「gochanTao」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/Gochan_Tao/article/details/107234845

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值