0

ケースステートメントで問題が発生しています。Python スクリプトは、センサー情報の場合は "s" を、リレー情報の場合は "r" を serial.writes します。センサー情報部分は完璧に機能します。リレー情報を正しく取得できません。Python スクリプトは、「r」に続いて、配列 [x] に格納する必要があるリレー情報を送信します。arduino は、case ステートメントの「r」を認識しますが、後続のパケットを処理しません。私が得るのは空の配列だけです。ここNick Gammons Serial pageを見ましたが、私の状況でそれを機能させる方法がわかりません.経験がありません.

どんな助けでも大歓迎です。

アルディーノコード

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] = '\0';
       started = true;
       ended = false;
    }
    else if(inChar == EOP)
    {
       ended = true;
       break;
    }
    else
    {
      if(index < 79)
      {
        inData[index] = inChar;
        index++;
        inData[index] = '\0';
      }
    }
  }

  // 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] = '\0';
  }
}
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()
4

1 に答える 1

0

はい、リレー機能に問題があると思います。また、c で文字列を終了するために「\0」が使用されるため、strtok に失敗する inData 配列に「\0」を挿入しすぎています。そのため、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] = '\0';
       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;
  }
}
于 2013-09-13T08:25:33.620 に答える