如何在C#中比较两个List并更新第一个List的指定字段?
解决方案
你的当前代码存在两个明显问题:一是嵌套循环导致时间复杂度为O(n*m)(n为学生数量,m为地址数量),数据量较大时效率极低;二是逻辑错误——每个学生会被所有地址依次覆盖更新,最终仅保留最后一个地址的数据,还会被重复添加多次到studentList中。
正确的做法是通过唯一标识关联学生与地址,从字段命名来看,Student.StudentNumber和AddressFromExternalAPI.SNumber应该是对应的关联键。我们可以先将地址列表转换为字典,以SNumber作为键,这样查找对应地址的时间复杂度降至O(1),整体效率提升为O(n+m)。
优化后代码(允许修改原Student对象)
public virtual IEnumerable<Student> GetStudentDetails(IEnumerable<Student> students) { // 将地址列表转换为字典,实现快速查找 var addressDict = getStudentAddress(students) .ToDictionary(address => address.SNumber); foreach (var student in students) { // 匹配到对应地址则更新学生信息 if (addressDict.TryGetValue(student.StudentNumber, out var address)) { student.StudentAddressLine1 = address.AddressLine1; student.StudentAddressLine2 = address.AddressLine2; student.StudentAddressPincode = address.Pincode; student.StudentAddressCity = address.City; student.StudentAddressState = address.State; } } return students; }
优化后代码(不修改原Student对象,保持不可变性)
如果需要避免修改原对象,可以创建Student的副本进行地址更新:
public virtual IEnumerable<Student> GetStudentDetails(IEnumerable<Student> students) { var addressDict = getStudentAddress(students) .ToDictionary(address => address.SNumber); return students.Select(student => { // 创建学生对象副本,保留原有非地址字段 var updatedStudent = new Student { StudentNumber = student.StudentNumber, StudentName = student.StudentName, StudentClass = student.StudentClass, StudentPhoneNumber = student.StudentPhoneNumber, StudentEmail = student.StudentEmail, StudentFatherPhoneNumber = student.StudentFatherPhoneNumber, StudentFatherEmail = student.StudentFatherEmail, StudentMotherPhoneNumber = student.StudentMotherPhoneNumber, StudentMotherEmail = student.StudentMotherEmail, // 默认保留原地址信息 StudentAddressLine1 = student.StudentAddressLine1, StudentAddressLine2 = student.StudentAddressLine2, StudentAddressPincode = student.StudentAddressPincode, StudentAddressCity = student.StudentAddressCity, StudentAddressState = student.StudentAddressState }; // 匹配到对应地址则更新副本的地址字段 if (addressDict.TryGetValue(student.StudentNumber, out var address)) { updatedStudent.StudentAddressLine1 = address.AddressLine1; updatedStudent.StudentAddressLine2 = address.AddressLine2; updatedStudent.StudentAddressPincode = address.Pincode; updatedStudent.StudentAddressCity = address.City; updatedStudent.StudentAddressState = address.State; } return updatedStudent; }); }
优化说明
- 效率提升:通过字典查找替代嵌套循环,时间复杂度从O(n*m)降至O(n+m),数据量越大,性能提升越显著。
- 逻辑修正:每个学生仅匹配对应的地址(如果存在),不会被重复更新或重复添加到列表。
- 代码简洁性:使用LINQ或单循环替代嵌套循环,逻辑更清晰易懂。
内容的提问来源于stack exchange,提问作者its me
相关产品推荐
相关产品推荐

