最快的方式来保存和解析一系列枚举?

时间:2012-04-04 00:14:35

标签: c# performance data-structures enums loops

在我创建的程序中,我有大量的枚举

enum kEvents
{
    Start = 0,
    End,
    EntityCreated,
}

在这个程序中,有一个庞大的实体列表。 每个实体都拥有一个“注册到”

的“kEvents”列表

每当一个对象说“调用开始事件”时,我必须遍历游戏中的每个实体,并找出他们是否正在“监听”该事件。

注意:我知道c#有事件处理程序,但我希望从头开始创建这个枚举系统。

在这种情况下,最好的方法是:

  1. 保存每个实体对象中的枚举集合
  2. 检查实体是否持有触发的枚举
  3. 我想知道Enums,基本上是数字,是否比List<T>个对象具有更低级别,更快速的处理方式。

3 个答案:

答案 0 :(得分:2)

  

每当一个对象说“调用开始事件”时,我必须遍历游戏中的每个实体,并找出他们是否正在“监听”该事件。

你做错了!迭代每个对象并检查它们是否注册了一个事件是非常低效的!这是典型的Observer design pattern,有几种方法可以解决这个问题,这里有几个:

  1. 有一个事件被引发并且具有事件类型的枚举参数(每个订阅者都获得它)。
  2. 有一个枚举和相应事件的字典。
  3. 以下是选项1 的外观:

    delegate void OnEventDelegate(kEvents anEvent);
    public class MyEventObservable
    {
        public event OnEventDelegate OnEvent;
    }
    
    public class MyEventObserver
    {
        // Constructors and all
        // ...
    
        public void OnEventReceived(kEvents anEvent)
        {
            switch(anEvent)
            {
                // switch through all the events and handle the ones that you need
            }
        }
    }
    
    MyEventObserver observer = new MyEventObserver();
    MyEventObservable observable = new MyEventObservable();
    observable.OnEvent += new OnEventDelegate(observer.OnEventReceived);
    

    以下是选项2

    public class MyEventObservable
    {
        private Dictionary<kEvents, List<IObserver>> _observers;
    
        MyEventObservable()
        {
            // Initialize the dictionary with all the events
        }
    
        public void RegisterObserver(kEvents event, IObserver observer)
        {
            _observers[event].Add(observer);
        }
    }
    
    interface class IObserver
    {    
        void Notify(kEvents anEvent);
    }
    
    public MyEventObserver: IObserver
    {
        // Constructors and all
        // ...
    
        // Override the IObserver
        public void Notify(kEvents anEvent)
        {
            switch(anEvent)
            {
                // switch through all the events and handle the ones that you need
            }
        }
    }
    
    MyEventObserver observer = new MyEventObserver();
    MyEventObservable observable = new MyEventObservable();
    observable.RegisterObserver(kEvents.Start, observer);
    

    选项二将减少每个观察者必须处理的事件数量,但这需要单独注册每个事件(这增加了编码复杂性)。这意味着选项2将更快地工作,因为要进行的函数调用较少。根据您希望获得性能的“疯狂”程度,可能还有其他选项可以帮助您加快速度,但这应该会让您走上正确的轨道。

    P.S。我没有编译任何代码,但它应该让你大致了解应该如何工作。

答案 1 :(得分:1)

在我看来,你想要实现某种发布/订阅方案,一些集中的事件接收实体可以订阅事件并在事件发生时提供回调,然后其他实体将升级事件和事件接收器将调用所有订阅该事件的实体....但我可能还没有理解这个问题:)

类似的东西:

How to access controls in other class

答案 2 :(得分:1)

  

每当一个对象说“调用Start事件”时,我必须迭代   通过游戏中的每个实体,并找出它们是否存在   “倾听”这一事件。

如果我正确地理解了你在做什么,那么你就是在倒退。实体正在监听哪些事件的知识不能(仅)在事件本身中。 必须是另一个保存此信息的数据结构。

其他数据结构可能就像从枚举常量到实体列表的Map一样简单。