c# - 循环列表空元素

标签 c# linq list class

我有一个包含类(人)实例的列表。随着时间的推移,有些人会消失(在列表中变为空),而另一些人会加入。然后我想遍历不为空的元素列表。

下面的代码可以完成这项工作,但我觉得它写得很糟糕。

  1. 我有一个包含许多空元素的列表。这甚至是一个问题吗?使用他当前的代码,它是易于管理的。但是如果我改变 createPerson(10);createPerson(300); , 和 for (int i = 1; i <= 100; i++)for (int i = 1; i <= 1000; i++) ,我的列表将包含约 6300 个元素,其中 6000 个为空。

  2. 逐个元素遍历列表并检查 if (person[i] != null)看起来很傻。还有其他方法吗?这里应该使用 LINQ 吗?

我在想也许最好删除空元素,然后将包含数据的元素移动到包含空的元素。然后我需要使用 person.Id (唯一的增量 ID),而不是索引号,来标识元素。类似于:

var item = person.First(i => i.Id == Id);

对于这个问题有什么推荐的方法吗?

代码

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace listID
{
    class Program
    {
        static List<People> person = new List<People>();
        static Random rnd = new Random();

        static void Main(string[] args)
        {
            // Generates 10 people of random ages.
            createPerson(10);

            // Advances 100 years.
            for (int i = 1; i <= 100; i++)
            {
                circleOfLife();
            }

            writeList();
            Console.ReadKey();
        }

        /// <summary>
        /// Writes out the current elements in the list
        /// </summary>
        static void writeList()
        {
            for (int i = 0; i < person.Count; i++)
            {
                if (person[i] != null)
                    Console.WriteLine("List index: " + i + " -  " + person[i].age + " years old.");
            }
        }


        /// <summary>
        /// Creates people of random age between 0 and 100.
        /// </summary>
        /// <param name="q">Amount of people to create</param>
        static void createPerson(int q)
        {
            for (int i = 1; i <= q; i++)
            {
                People newPerson = new People();
                newPerson.age = rnd.Next(100);
                person.Add(newPerson);
            }
        }

        /// <summary>
        /// Increases age of person by a year. If person reaches age of 100, they get removed, and another one of random age is added.
        /// </summary>
        static void circleOfLife()
        {
            for (int i = 0; i < person.Count; i++)
            {
                if(person[i] != null)
                {
                    person[i].increaseAge();
                    if (person[i].age > 99)
                    {
                        person[i] = null;
                        createPerson(1);
                    }
                }
            }
        }

    }

    class People
    {
        public int age;

        private static int m_Counter = 0;
        public int Id { get; set; }
        public People()
        {
            this.Id = System.Threading.Interlocked.Increment(ref m_Counter); // Gives unique incrememntal ID number to each elelment.
        }

        public void increaseAge()
        {
            age++;
        }

    }
}

输出:

List index: 13 -  93 years old.
List index: 17 -  26 years old.
List index: 18 -  95 years old.
List index: 19 -  45 years old.
List index: 20 -  34 years old.
List index: 21 -  92 years old.
List index: 22 -  58 years old.
List index: 23 -  44 years old.
List index: 24 -  67 years old.

非常感谢您的帮助。我仍在学习,所以示例代码会非常有用。

最佳答案

你为什么不替换人而不是分配给null并添加?

 static void circleOfLife() {
   for (int i = 0; i < persons.Count; ++i) {
     persons[i].increaseAge();

     // if a person is too old  
     if (persons[i].age > 99) {
       // ...generate a new person and put it on old person's place
       persons[i] = new People() {
         age = rnd.Next(100)
       }; 
     }
   } 
 }

在这种情况下,您将摆脱讨厌的 null 检查。

关于c# - 循环列表空元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39429308/

相关文章:

c# - 将 C# 委托(delegate)与具有可选参数的方法一起使用

C# 检查 COM(串行)端口是否已经打开

c# - 使用 linq 将列表列表转换为单个列表

linq - 管理 LINQ to SQL .dbml 模型复杂性

sql-server - 如果存在相同的值,例如给定的产品名称,如何在 SQL Server 中组合行?

python - 如何替换与我的字符串列表匹配的单词(在 txt 文件中)?

c# - 保存发送给机器人的用户消息并将完成的表格发送给其他用户

c# - 我如何使用 MVC.Net 模型绑定(bind) 'List<SelectItem>' 的列表

c# - 使用哪种对象集合类型?

python - 如何多次循环访问相同的列表?