2014-11-12 2 views
-2

У меня есть поток, который должен работать непрерывно в моей программе и анализировать входящие последовательные данные из коллекции датчиков.Thread with while (true) loop выходит как-то

//initialized as a global variable 
System.Threading.Thread processThread = new System.Threading.Thread(ProcessSerialData); 

//this gets called when you press the start button 
processThread.Start(); 

private void ProcessSerialData() 
{ 
    while (true) 
    { 
     //do a whole bunch of parsing stuff 
    } 
    int howDidYouGetHere = 0; 
} 

Как возможно, что моя программа достигает линии «int howDidYouGetHere = 0»?

Полный код можно найти здесь:

/// <summary> 
    /// ProcessSerialData thread will be used to continue testing the connection to the controller, 
    /// process messages in the incoming message queue (actually a linked list), 
    /// and sends new messages for updated data. 
    /// </summary> 
    /// <param name="sender"></param> 
    /// <param name="e"></param> 
    private void ProcessSerialData() 
    { 
     while (true) 
     { 
      UpdateAhTextbox(test.ampHoursOut.ToString()); 

      if (!relayBoard.OpenConn()) 
      { 
       MessageBox.Show("Connection to controller has been lost."); 
       testInterrupted = "Lost connection. Time = " + test.duration; 
       UpdateStatusText(false); 
       ShutErDown(); 
      } 

      ///////////////////////////////////////////////////// 
      if (incomingData.Count > 0) 
      { 
       string dataLine = ""; 
       try 
       { 
        dataLine = incomingData.First(); 
        UpdateParsedDataTextbox(dataLine + "\r\n"); 
       } 
       catch (System.InvalidOperationException emai) 
       { 
        break; //data hasn't come in yet, it will by the time this runs next. 
       } 

       incomingData.RemoveFirst(); 

       if (dataLine.Contains("GET")) // some sensor values (analog/temp/digital) has come in 
       { 
        if (dataLine.Contains("GETANALOG")) // an analog value has come in 
        { 
         int index = dataLine.IndexOf("CH"); 
         int pin = (int)Char.GetNumericValue(dataLine[index + 2]); 

         double value = 0; 
         int dataLineLength = dataLine.Length; 
         if (dataLineLength > 13) // value is appended to end of line 
         { 
          try 
          { 
           value = Convert.ToDouble(dataLine.Substring(13)); 
          } 
          catch // can't convert to double 
          { 
           int index2 = dataLine.IndexOf("CH", 3); 
           if (index2 != -1) // there happen to be two sets of commands stuck together into one 
           { 
            string secondHalf = dataLine.Substring(index2); 
            incomingData.AddFirst(secondHalf); 
           } 
          } 
         } 
         else // value is on the next line 
         { 
          try 
          { 
           value = Convert.ToDouble(incomingData.First()); 
           incomingData.RemoveFirst(); 
          } 
          catch // can't convert to double 
          { 
           MessageBox.Show("Error occured: " + dataLine); 
          } 
         } 
         switch (pin) 
         { 
          case 1: 
           ReadVoltage(value); 
           break; 
          case 2: 
           ReadAmperage(value); 
           break; 
         } 
        } 
        else if (dataLine.Contains("GETTEMP")) // received reply with temperature data 
        { 
         int index = dataLine.IndexOf("CH"); 
         int pin = (int)Char.GetNumericValue(dataLine[index + 2]); // using index of CH, retrieve which pin this message is coming from 

         double value = 0; 
         int dataLineLength = dataLine.Length; 
         if (dataLineLength > 11) // value is appended to end of line 
         { 
          try 
          { 
           value = Convert.ToDouble(dataLine.Substring(11)); 
          } 
          catch // can't convert to double 
          { 
           int index2 = dataLine.IndexOf("CH", 3); 
           if (index2 != -1) // there happen to be two sets of commands stuck together into one 
           { 
            string secondHalf = dataLine.Substring(index2); 
            incomingData.AddFirst(secondHalf); 
           } 
          } 
         } 
         else // value is on the next line 
         { 
          value = Convert.ToDouble(incomingData.First()); 
          incomingData.RemoveFirst(); 
         } 
         ReadTemperature(pin, value); 
        } 
        else // must be CH3.GET 
        { 
         int index = dataLine.IndexOf("CH"); 
         int pin = (int)Char.GetNumericValue(dataLine[index + 2]); // using index of CH, retrieve which pin this message is coming from 

         if (pin == 3) // only care if it's pin 3 (BMS), otherwise it's a mistake 
         { 
          double value = 0; 
          int dataLineLength = dataLine.Length; 
          if (dataLineLength > 7) // value is appended to end of line 
          { 
           try 
           { 
            value = Convert.ToDouble(dataLine.Substring(7)); 
           } 
           catch // can't convert to double 
           { 
            int index2 = dataLine.IndexOf("CH", 3); 
            if (index2 != -1) // there happen to be two sets of commands stuck together into one 
            { 
             string secondHalf = dataLine.Substring(index2); 
             incomingData.AddFirst(secondHalf); 
            } 
           } 
          } 
          else // value is on the next line 
          { 
           value = Convert.ToDouble(incomingData.First()); 
           incomingData.RemoveFirst(); 
          } 
          ReadBMS(value); 
         } 
        } 
       } 
       else if (dataLine.Contains("REL")) // received reply about relay turning on or off. 
       { 
        if (dataLine.Contains("RELS")) // all relays turning on/off 
        { 
         if (dataLine.Contains("ON")) 
         { 
          for (int pin = 1; pin <= 4; pin++) 
          { 
           test.contactors[pin] = true; 
          } 
         } 
         else // "OFF" 
         { 
          for (int pin = 1; pin <= 4; pin++) 
          { 
           test.contactors[pin] = false; 
          } 
         } 
        } 
        else // single relay is turning on/off 
        { 
         int index = dataLine.IndexOf("REL"); 
         int pin = (int)Char.GetNumericValue(dataLine[index + 3]); 

         if (dataLine.Contains("ON")) 
         { 
          test.contactors[pin] = true; 
         } 
         else if (dataLine.Contains("OFF")) 
         { 
          test.contactors[pin] = false; 
         } 
         else if (dataLine.Contains("GET")) 
         { 
          if (Convert.ToInt32(incomingData.First()) == 1) 
           test.contactors[pin] = true; 
          else 
           test.contactors[pin] = false; 
          incomingData.RemoveFirst(); 
         } 
        } 
       } 
      } 
      ///////////////////////////////////////////////////// 

      // we only want more data if we're done processing the current data, otherwise we're stuck with too much and processing is heavily delayed. 
      if (isTestRunning && incomingData.Count < 3) 
      { 
       //read & output v, a, bms state 
       sendToController("CH1.GETANALOG"); // get voltage 
       sendToController("CH2.GETANALOG"); // get amperage 
       sendToController("CH3.GET"); // get BMS state 

       //read & output temperature 
       sendToController("CH4.GETTEMP"); // get temperature 
       sendToController("CH5.GETTEMP"); 

       string lines = "Ah Out: " + test.ampHoursOut + ", Voltage: " + test.voltage + 
        ", Amperage: " + test.amperage + ", Cell Temperature: " + test.tempBattery + 
        ", Load Temperature: " + test.tempLoad; 
       WriteToLog(lines); 
      } 
     } 
     int howDidYouGetHere = 0; 
    } 
+1

Вместо перерыва попробуйте продолжить. – Middas

+0

По какой-то причине мой try-catch не вызывает исключения, поэтому мне нужно найти более всеобъемлющее решение для этого. Читайте о замках сейчас, спасибо! – jules0075

ответ

2

break (без учета тех, кто внутри вложенной switch) вспыхивает из цикла while.

+1

Возможно, вместо этого предполагается использовать OP. – Jason

+0

Разрыв не выходит из цикла while. Это правильный синтаксис для операторов switch (http://msdn.microsoft.com/en-us/library/06tc147t.aspx). Моя программа будет работать до 40 секунд, а затем выйти из цикла while. В то время этот оператор break попадает до 100 раз. – jules0075

+2

Перерыв в вашем блоке 'catch'. –

-1

Возможно, вы попытались обновить свой пользовательский интерфейс, используя UpdateParsedDataTextbox. Это вызовет InvalidOperationException (тогда разрывает цикл while), потому что вы пытаетесь получить доступ к элементу управления пользовательского интерфейса из потока, который не владеет элементом управления.

+0

Исключение приведет к завершению цикла, но это не приведет к коду непосредственно после окончания цикла. Исключение закончило бы проталкивание мимо любого такого кода, пока оно не попадет в соответствующий блок catch. – Servy

+0

@Servy Это также может занять место. –