C# foreach循环内调用Append向数组添加对象不生效问题求解
问题根因
你的代码有3个核心逻辑错误,直接导致元素没有存入数组:
- C#中的数组是固定长度结构,你初始化时写
ExerciseAnswer[] exerciseAnswers = new ExerciseAnswer[2]就已经锁定了数组长度,本身不支持动态追加扩容。 - 你调用的
Append()是LINQ扩展方法,不会修改原数组,只会返回一个拼接了新元素的全新序列,你没有接收这个返回值,等于这行代码完全没产生实际效果。 - 你用foreach遍历初始全为null的定长数组来赋值的逻辑本身不成立:foreach是用来遍历读取集合元素的,循环中拿到的是数组存储值的拷贝,修改这个拷贝不会影响原数组对应位置的内容。
修正方案
根据你的需求选一种实现即可:
方案1:固定答案数量时直接用for循环按索引给数组赋值
如果提前确定答案总数固定,不需要动态增减,直接用for循环定位到数组索引位赋值,完全不需要调用Append:
static void CreateNewExerciseTest() { string? exerciseName = "Test Exercise"; string? exerciseTopic = "Test"; string exerciseQuestion = "Does it work?"; int numberOfAnswers = 2; int numberOfApplicableAnswers = 0; ExerciseAnswer[] exerciseAnswers = new ExerciseAnswer[numberOfAnswers]; for (int i = 0; i < exerciseAnswers.Length; i++) { int exerciseAnswerId = GenerateId(); Console.WriteLine("\nEnter a name for this Exercise answer: "); string? exerciseAnswerName = Console.ReadLine(); Console.WriteLine("Enter this answer for the Exercise: "); string exerciseAnswerContent = Console.ReadLine(); Console.WriteLine("Enter y (yes) if this Exercise answer is applicable, otherwise press n (no) or any other key: "); char applicableAnswer = Console.ReadKey().KeyChar; // 吃掉ReadKey遗留的换行符,避免后续ReadLine读入空值 Console.ReadLine(); bool applicable = ExerciseAnswer.EvaluateExerciseAnswer(applicableAnswer); if (applicable) { numberOfApplicableAnswers++; } exerciseAnswers[i] = new ExerciseAnswer(exerciseAnswerId, exerciseAnswerName, exerciseAnswerContent, applicable); } // 后续构建Exercise对象的逻辑 }
方案2:需要动态调整答案数量时用List代替数组
如果后续可能增减答案数量,不要用定长数组,改用支持动态扩容的List<ExerciseAnswer>,调用原生Add方法即可追加元素:
static void CreateNewExerciseTest() { string? exerciseName = "Test Exercise"; string? exerciseTopic = "Test"; string exerciseQuestion = "Does it work?"; int numberOfAnswers = 2; int numberOfApplicableAnswers = 0; // 初始化动态列表,不需要提前固定长度 List<ExerciseAnswer> exerciseAnswers = new List<ExerciseAnswer>(); for (int i = 0; i < numberOfAnswers; i++) { int exerciseAnswerId = GenerateId(); Console.WriteLine("\nEnter a name for this Exercise answer: "); string? exerciseAnswerName = Console.ReadLine(); Console.WriteLine("Enter this answer for the Exercise: "); string exerciseAnswerContent = Console.ReadLine(); Console.WriteLine("Enter y (yes) if this Exercise answer is applicable, otherwise press n (no) or any other key: "); char applicableAnswer = Console.ReadKey().KeyChar; Console.ReadLine(); bool applicable = ExerciseAnswer.EvaluateExerciseAnswer(applicableAnswer); if (applicable) { numberOfApplicableAnswers++; } ExerciseAnswer exerciseAnswer = new ExerciseAnswer(exerciseAnswerId, exerciseAnswerName, exerciseAnswerContent, applicable); // List的Add方法会直接修改原列表,把元素存入集合 exerciseAnswers.Add(exerciseAnswer); } // 如果后续逻辑必须接收数组类型,最后调用ToArray转换即可 // ExerciseAnswer[] finalAnswerArr = exerciseAnswers.ToArray(); }
额外优化提示
- 布尔值判断不需要写
if (applicable == true),直接写if (applicable)即可 - 你代码里的
numberOfAnswers变量声明后没有实际用到,初始化数组/循环边界直接用这个变量即可,不要硬编码长度2
内容的提问来源于stack exchange,提问作者Daniel
相关产品推荐
相关产品推荐

