向列表添加元素却出现重复值问题求助(Dart)
问题描述
我有一个名为LedColChangeDate2的类,其构造函数接收多个参数,类内包含一个自身类型的静态列表。在另一个类中,我定义了addLedToList方法,该方法使用自身类的若干列表创建LedColChangeDate2实例,并将其添加到LedColChangeDate2的静态列表中。但每次调用addLedToList方法传入不同值时,新添加实例的数值会被复制到列表的所有元素中。我意识到这与引用变量有关,于是尝试修改最新添加元素的字段:
int ind = LedColChangeDate2.ledList.length - 1; print('index = $ind'); LedColChangeDate2.ledList[ind].fadeToTime = fadeOnTimes;
但这并没有起到任何作用,希望能得到帮助。
相关代码
LedColChangeDate2类
class LedColChangeDate2 { static List<LedColChangeDate2> ledList = []; LedColChangeDate2({ required this.ledNo, // int ( not a list) required this.codeList, // list of strings required this.fadeToTime, // list of strings required this.stayOnTime, // list of strings required this.colorList, // list colors }); late int ledNo; List<String> codeList = []; List<String> fadeToTime = []; List<String> stayOnTime = []; List<Color> colorList = []; static bool listCreated = false; static void printLedDetails() { for (int i = 0; i < ledList.length; i++) { print('item no $i'); print(ledList[i].ledNo); print('Colours'); _printList(ledList[i].colorList); print('codes'); _printList(ledList[i].codeList); print('Fade times'); _printList(ledList[i].fadeToTime); print('stay on times'); _printList(ledList[i].stayOnTime); } } static void _printList(List inputList) { for (int i = 0; i < inputList.length; i++) { print(' $i // ${inputList[i]} '); } } }
addLedToList方法
void addLedToList() { print('adding LED to list **************'); var obj = LedColChangeDate2( ledNo: 1, codeList: colCodes, fadeToTime: fadeOnTimes, stayOnTime: stayOnTimes, colorList: storedColours); LedColChangeDate2.ledList.add(obj); int ind = LedColChangeDate2.ledList.length - 1; print('index = $ind'); LedColChangeDate2.ledList[ind].fadeToTime = fadeOnTimes; LedColChangeDate2.printLedDetails(); }
解决方案
问题核心是所有LedColChangeDate2实例共享了同一个列表引用。Dart中列表是引用类型,当你把colCodes、fadeOnTimes等列表直接传给构造函数时,所有实例的对应字段都指向同一个内存地址的列表。后续修改这些列表内容时,所有实例的字段都会同步变化。
解决方法是在构造实例时,为每个列表创建独立的副本,而不是直接传递原列表的引用:
方式一:修改类的构造函数
在LedColChangeDate2的构造函数内部,自动对传入的列表进行复制,确保每个实例拥有独立的列表:
class LedColChangeDate2 { static List<LedColChangeDate2> ledList = []; LedColChangeDate2({ required this.ledNo, required List<String> codeList, required List<String> fadeToTime, required List<String> stayOnTime, required List<Color> colorList, }) : codeList = List.from(codeList), fadeToTime = List.from(fadeToTime), stayOnTime = List.from(stayOnTime), colorList = List.from(colorList); late int ledNo; final List<String> codeList; final List<String> fadeToTime; final List<String> stayOnTime; final List<Color> colorList; // 其余方法保持不变... }
方式二:实例化时主动传入列表副本
在调用构造函数创建实例时,手动为每个列表生成副本:
void addLedToList() { print('adding LED to list **************'); var obj = LedColChangeDate2( ledNo: 1, codeList: List.from(colCodes), fadeToTime: List.from(fadeOnTimes), stayOnTime: List.from(stayOnTimes), colorList: List.from(storedColours)); LedColChangeDate2.ledList.add(obj); LedColChangeDate2.printLedDetails(); }
为什么之前的修改无效?
你之前尝试重新赋值fadeToTime,但依然传入的是同一个fadeOnTimes引用,本质上还是让所有实例共享同一个列表,所以没有效果。只有创建独立的列表副本,才能让每个实例拥有自己的列表数据。
内容的提问来源于stack exchange,提问作者dazz500
相关产品推荐
相关产品推荐

