C# 物业更改通知书

C# 物业更改通知书,c#,.net,multithreading,twitter,queue,C#,.net,Multithreading,Twitter,Queue,你好,我有一个有很多背景工作人员的程序。这些背景工作人员什么都不做,只听一个名为tweet的变量的变化,然后每个背景人员为每条tweet创建一个任务来处理它,并准备处理另一条tweet 下面是每1秒或更短时间更新一次的Tweet类 Tweet tweet = new Tweet(); public class Tweet : INotifyPropertyChanged { private ITweet lastTweet; protecte

你好,我有一个有很多背景工作人员的程序。这些背景工作人员什么都不做,只听一个名为tweet的变量的变化,然后每个背景人员为每条tweet创建一个任务来处理它,并准备处理另一条tweet

下面是每1秒或更短时间更新一次的Tweet类

  Tweet tweet = new Tweet();
    public class Tweet : INotifyPropertyChanged
    {
        private ITweet lastTweet;

        protected void OnPropertyChanged(PropertyChangedEventArgs e)
        {
            PropertyChangedEventHandler handler = PropertyChanged;
            if (handler != null)
                handler(this, e);
        }

        protected void OnPropertyChanged(string propertyName)
        {
            OnPropertyChanged(new PropertyChangedEventArgs(propertyName));
        }

        public ITweet LastTweet
        {
            get { return lastTweet; }
            set
            {
                if (value != lastTweet)
                {
                    lastTweet = value;
                    OnPropertyChanged("LastTweet");
                }
            }
        }

        public event PropertyChangedEventHandler PropertyChanged;
    }
现在在我的BackgroundWorker DoWork实现中:

        Del OnNewTweetEvent = delegate(object sender2, PropertyChangedEventArgs args)
        {
            Task task = null;
            task = new Task(() =>
            {
                var mytweet = sender2 as Tweet;
                var tweetText = mytweet.LastTweet.Text;
                //copy the tweetText in case the mytweet variable changed ( not sure )
                ProcessTweet( tweetText );
            });
            task.Start();

        };
        this.tweet.PropertyChanged += new PropertyChangedEventHandler(OnNewTweetEvent);

        //wait and prepare for cancellation
        var backgroundworker = sender as BackgroundWorker;
        while (true)
        {
            Thread.Sleep(10);
            if (backgroundworker.CancellationPending)
            {
                //remove the notification
                this.tweet.PropertyChanged -= new PropertyChangedEventHandler(OnNewTweetEvent);
                return;
            }
        }
    }
这个代码逻辑正确吗?如果tweets源每0.01秒发送一次tweets,我是否能够获取所有tweets?或者推文可能会在我的背景工作人员没有收到的情况下更改

排队还是什么的好?
感谢您的帮助。

正如您已经怀疑的那样,您的示例中的方法可能无法捕获每一条tweet或保证每一条tweet只处理一次。因此,您应该将它们存储在集合中。队列非常适合用于此目的

更直接的方法是让一个后台任务监视队列,并启动一个异步任务来处理队列中的新tweet

但是,需要有人将Tweet放在队列或示例中,以更新Tweet对象的属性。因此,最简单、最好的方法是在新tweet到达时立即启动异步任务。这消除了等待新tweet的后台任务,并由此消除了系统可能中断的位置

基于您的代码示例,下面的代码展示了一种在新tweet到达时处理它的简单方法。您可能希望将代码移动到代码中的另一个位置,并根据需要重命名类型。根据您的评论,此示例还考虑了不同推文类型的不同操作:

// No need to implement INotifyPropertyChanged as there is no listener anymore
public class Tweet 
{
    private ITweet lastTweet;

    public ITweet LastTweet
    {
        get { return lastTweet; }
        set
        {
            if (value != lastTweet)
            {
                lastTweet = value;
                var actionForTweet = GetActionForTweet(lastTweet);
                Task task = new Task(() =>
                {
                    actionForTweet(lastTweet);
                });
                task.Start();
            }
        }
    }

    private static Action<ITweet> GetActionForTweet(ITweet tweet)
    {
        // Decide what to do for which kind of tweet
        // In the simplest case this is an if/switch statement
        if ( ... )
              return x => {
                              var tweetText = x.Text;
                              ProcessTweet( tweetText );
                          };
        else 
              return x => {
                              // Do something else
                          };
    }
}

谢谢你的回复。你能为我当前的代码提供一些代码编辑,告诉我最好的方法吗?@circler:我添加了一个小示例。希望能有帮助。谢谢你的代码。作为一个集合,最好的方法是什么,因为我想在后台工作程序中运行它,因为每个工作程序都有不同的事情要做。@circler:我已经更新了示例,使其能够为不同的tweet做不同的事情。我想你不需要排队。我对您的项目了解不多,所以请不要期望一个不经过修改或采用就适合您的特定环境的示例。希望我的想法能有所帮助。