【问题标题】:A While Loop Thread一个 While 循环线程
【发布时间】:2012-10-28 09:15:10
【问题描述】:

所以我一直在尝试创建一些代码,在 while 循环中发送数据,特别是通过 UdpClient 将活动数据包发送到服务器。

 static void doSend(string ip, int port)
    {
        while (isSending)
        {
            _sockMain = new UdpClient(ip, port);
            // Code for datagram here, took it out
            _sockMain.Send(arr_bData, arr_bData.Length);
        }
    }

但是当我调用“Stop”方法时,它会卡在一个恒定的循环中并且不会出来。如何将while循环放入线程?所以我可以在停止时中止线程,取消循环?

【问题讨论】:

  • 如果你从不改变变量isSending,你永远不会退出循环
  • 是的,当我按下按钮时 isSending = false 但它就是不退出。
  • 那么问题可能不在你的循环中,而在数据报代码的某个地方。
  • 您需要发布更多代码,这还不够
  • 也许是,AmazingDreams...而且,我很抱歉 Alan...

标签: c# while-loop


【解决方案1】:

使用BREAK 语句怎么样?

【讨论】:

【解决方案2】:
static bool _isSending;

static void doSend(string ip, int port)
{
    _isSending = true;

    while (_isSending)
    {
        _sockMain = new UdpClient(ip, port);
        // ...
        _sockMain.Send(arr_bData, arr_bData.Length);
    }
}

static void Stop()
{
    // set flag for exiting loop here
    _isSending = false;    
}

还可以考虑用 PascalCase 命名您的方法,即DoSend(甚至StartSending 会更好)、StopSending

【讨论】:

  • 谢谢你,但它挂起?接收程序仍然获取数据。
  • 因为你是循环发送的。当前发送完成后,不会发生下一个。
【解决方案3】:

可以使用后台工作线程http://www.dotnetperls.com/backgroundworker 并在 dowork() 内放置您的 while 循环。 您可以使用 CancelAsync() 停止代码并设置backgroundWorker1.WorkerSupportsCancellation == true

BackgroundWorker bw = new BackgroundWorker();
          if (bw.IsBusy != true)
          {
              bw.RunWorkerAsync();

          }

          private void bw_DoWork(object sender, DoWorkEventArgs e)
          {
              // Run your while loop here and return result.
              result = // your time consuming function (while loop)
          }

          // when you click on some cancel button  
           bw.CancelAsync();

【讨论】:

  • 这样不行。您需要设置 WorkerSupportsCancellation 并且必须在循环中检查 CancellationPending。一个完整的例子可以在MSDN找到。
【解决方案4】:

它挂起是因为您的 doSend 方法适用于 UI 线程。您可以使用类似下面的类使其在单独的线程上运行,也可以使用BackgroundWorkerClass

public class DataSender
    {
        public DataSender(string ip, int port)
        {
            IP = ip;
            Port = port;
        }

        private string IP;
        private int Port;
        System.Threading.Thread sender;
        private bool issending = false;

        public void StartSending()
        {
            if (issending)
            {
                // it is already started sending. throw an exception or do something.
            }
            issending = true;
            sender = new System.Threading.Thread(SendData);
            sender.IsBackground = true;
            sender.Start();
        }

        public void StopSending()
        {
            issending = false;
            if (sender.Join(200) == false)
            {
                sender.Abort();
            }
            sender = null;
        }

        private void SendData()
        {
            System.Net.Sockets.UdpClient _sockMain = new System.Net.Sockets.UdpClient(IP, Port);
            while (issending)
            {
                // Define and assign arr_bData somewhere in class
                _sockMain.Send(arr_bData, arr_bData.Length);
            }
        }
    }

【讨论】:

  • 我喜欢这个!谢谢塔纳!
  • 太糟糕了! volatile 没有在任何答案中提及。
  • @AlexanderPetrov 这可能是因为 volatile 关键字是在几年后添加的!
猜你喜欢
  • 2015-06-14
  • 2014-05-27
  • 1970-01-01
  • 1970-01-01
  • 2014-08-03
  • 2013-01-12
  • 2011-06-12
  • 2018-11-29
  • 1970-01-01
相关资源
最近更新 更多