C # - событие, которое запускается, когда список не пуст - PullRequest
0 голосов
/ 16 мая 2011

Эй, я сейчас создаю программу, в которой у меня есть несколько списков информации.Когда записи в списке 1 будут обработаны, они будут удалены из списка 1 и добавлены в список 2. Когда записи в списке 2 будут обработаны, они будут удалены и добавлены в список 3 и так далее.При обработке списка все элементы, присутствующие в начале обработки, будут удалены из списка.Записи будут добавляться во все списки непрерывно, пока работает программа, и непредсказуемым образом.Новые записи должны будут обрабатываться довольно быстро.

Я полагал, что лучший способ добиться этого - каждый список вызывать событие при добавлении чего-либо и выполнять действие.Чтобы сделать мою жизнь проще, я создал собственный класс списка, который принимает Action в качестве параметра конструктора, и вызывал это Action при каждом запуске события (см. Код).Однако способ, которым я реализовал это, когда событие вызывается, когда что-то добавляется в список, является ужасно неэффективным, с множеством новых записей за короткий промежуток времени.события, которые запускаются всякий раз, когда список не пуст.Кроме того, есть ли хороший способ убедиться, что событие не будет запущено снова, если оно уже было запущено и все еще «активно» (в отсутствии лучшего объяснения).непонятно, так и скажите, а я попробую уточнить.Спасибо!

    public class EventDrivenList<T> : List<T>
    {
        private Action action_on_list_change;
        private delegate void ListChangedDelegate(object sender, EventArgs e);
        private event ListChangedDelegate ListChangedEvent;

        private List<T> unprocessed_items; 
        public List<T> List
        {
            get
            {
                lock (unprocessed_items)
                {
                    return unprocessed_items;
                }
            }
        }

        public EventDrivenList(Action action, int size)
        {
            action_on_list_change = action;
            unprocessed_items = new List<T>(size);
            ListChangedEvent += new ListChangedDelegate(OnChangeMethod); 
        }

        public EventDrivenList(Action action)
        {
            action_on_list_change = action;
            unprocessed_items = new List<T>();
            ListChangedEvent += new ListChangedDelegate(OnChangeMethod); 
        }

        ~EventDrivenList()
        {
            ListChangedEvent -= new ListChangedDelegate(OnChangeMethod);
        }

        private void OnChange(EventArgs e)
        {
            if (ListChangedEvent != null)
                ListChangedEvent(this, e);
        }

        private void OnChangeMethod(object sender, EventArgs e)
        {   
             action_on_list_change.Invoke();            
        }

        new public void Add(T item)
        {
            lock (unprocessed_items)
            {
                unprocessed_items.Add(item);
            }
            OnChange(EventArgs.Empty);
        }

        new public void Remove(T item)
        {
            lock (unprocessed_items)
            {
                unprocessed_items.Remove(item);
            }
        }

        new public int Count()
        {
            lock (unprocessed_items)
            {
                return unprocessed_items.Count;
            }
        }
    }

Ответы [ 3 ]

1 голос
/ 16 мая 2011

Вы смотрели на ObservableCollection?Он имеет событие een CollectionChanged по умолчанию, которое срабатывает, когда что-то изменяется в списке.http://msdn.microsoft.com/en-us/library/ms653375.aspx

1 голос
/ 16 мая 2011

Что касается вашего беспокойства по поводу дублирующих / перекрывающихся срабатываний, вариант: создать обработчик, который «разводит» все обработчики во время его обработки (а затем повторно подключает их, когда завершает обработку).

0 голосов
/ 16 мая 2011

Если я правильно понял, ваша проблема может быть решена с помощью ManualResetEvent. Событие будет срабатывать и оставаться активным при добавлении элемента, и элементы будут продолжать присутствовать в списке (то есть непусто). Когда список пуст, вы можете просто сбросить событие ...

ObservableCollection - это еще один вариант ... однако при каждом добавлении или удалении элемента будет запускаться событие CollectionChanged, которое будет аналогично тому, что вы в настоящее время делаете вручную ...

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...