解析 Arduino 和 Python 之间的 case 语句中的串行通信,在 1st char 之后



我在案例陈述中遇到了问题。python脚本要么为传感器信息写入"s",要么为继电器信息写入"r"。传感器信息部分工作完美。我在正确获取中继信息时遇到问题。python 脚本发出一个 "r",后跟中继信息,这些信息应该存储在 array[x] 中。arduino 确认 case 语句中的"r",但不处理随后的后续数据包。我得到的只是空数组。我在这里看了一下尼克·金蒙斯系列页面,但无法弄清楚如何在我的情况下让它工作,我只是没有经验。

任何帮助都非常感谢。

阿杜伊诺代码

void SerialCommunication()
{ 
  if (Serial.available()>0)
  {
    char inChar = Serial.read(); 
    switch (inChar) 
    {
      case 'r':
        Sensors();
        break;
      case 'w':
        Relays();
        ProcessRelays();
        break;
      default:
        break;
    }
  } 
}
void Relays()
{
  while (Serial.available() ==0);
  // Read all serial data available, as fast as possible
  while(Serial.available() > 0)
  {
    char inChar = Serial.read();
    if(inChar == SOP)
    {
       index = 0;
       inData[index] = '';
       started = true;
       ended = false;
    }
    else if(inChar == EOP)
    {
       ended = true;
       break;
    }
    else
    {
      if(index < 79)
      {
        inData[index] = inChar;
        index++;
        inData[index] = '';
      }
    }
  }
  // We are here either because all pending serial
  // data has been read OR because an end of
  // packet marker arrived. Which is it?
  if(started && ended)
  {
    // The end of packet marker arrived. Process the packet
    if (strlen(inData) > 0)
   {
      char *token = strtok(inData, ",");
      if(token)
      {
         index = 0;
         array[index] = atoi(token);
         while (token = strtok(NULL, ","))
         {
            array[index++] = atoi(token);
         }
      }
    }
    // Reset for the next packet
    started = false;
    ended = false;
    index = 0;
    inData[index] = '';
  }
}
void ProcessRelays()
{
  Serial.println(array[0]);
  Serial.println(array[1]);
  Serial.println(array[2]);
}

蟒蛇代码

#Import libraries
import serial
import string
import MySQLdb
import pprint
from time import strftime
#Connect to arduino
ser = serial.Serial('/dev/ttyACM0', baudrate=9600, timeout = 2)
ser.open()
#Connects to database
db = MySQLdb.connect(host="localhost", # your host, usually localhost
                     user="zzz", # your username
                     passwd="zzz", # your password
                     db="zzz") # name of the data base

cur = db.cursor()
with db:
        cur = db.cursor()
        cur.execute("SELECT * FROM relayschedule WHERE id=1")
        rows = cur.fetchall()
    for row in rows:
        s = str(row)
        ser.write("w" + s)
ser.close()
db.close()
是的,

我认为您的中继功能可能存在一些问题。此外,您插入了太多的"\0"在您的 inData 数组中,该数组将失败 strtok,因为 '\0' 用于终止 C 中的字符串。因此,如果strtok在输入字符串(inData)中间看到"\0",它将终止处理。我想你可以试试这种方式。这与你正在做的与 inData 相关的一些更改几乎相同。

void Relays()
{
  while (Serial.available() ==0);
  // Read all serial data available, as fast as possible
  while(Serial.available() > 0)
  {
    char inChar = Serial.read();
    if(inChar == SOP)
    {
       index = 0;
       started = true;
       ended = false;
    }
    else if(inChar == EOP)
    {
       ended = true;
       inData[index] = '';
       break;
    }
    else
    {
      if(index < 79)
      {
        inData[index] = inChar;
        index++;
      }
    }
  }
  // We are here either because all pending serial
  // data has been read OR because an end of
  // packet marker arrived. Which is it?
  if(started && ended)
  {
    // The end of packet marker arrived. Process the packet
    if (strlen(inData) > 0)
   {
      char *token = strtok(inData, ",");
      if(token)
      {
         index = 0;
         array[index] = atoi(token);
         while (token = strtok(NULL, ","))
         {
            array[index++] = atoi(token);
         }
      }
    }
    // Reset for the next packet
    started = false;
    ended = false;
    index = 0;
  }
}

最新更新