23

arduinoで行うタスクがいくつかありますが、そのうちの1つは非常に時間がかかるため、スレッドを使用して同時に実行することを考えていました。私はArduinoメガを持っています

[更新] ついに 4 年後、私の arduino メガに FreeRTOS をインストールできるようになりました。ここにリンクがあります

4

11 に答える 11

16

要するに:いいえ。しかし、あなたはそれを試してみることができます: http ://www.kwartzlab.ca/2010/09/arduino-multi-threading-librar/

于 2012-12-22T12:59:16.647 に答える
7

まだですが、大きなプロジェクトでは常にこのライブラリを使用しています: https://github.com/ivanseidel/ArduinoThread

タイマー割り込み内にコールバックを配置すると、出来上がりです。Arduinoで実行されている疑似スレッドがあります...

于 2013-12-08T14:36:34.633 に答える
6

このスレッドをより完全にするために、メモリフットプリントが非常に小さく(私の記憶が正しければ数バイト)、スレッドローカルの変数を保持するプロトスレッドもあります。非常に便利で時間を節約できます (有限状態マシンがはるかに少ない -> より読みやすいコード)。

例とコード: arduino-class / ProtoThreads wiki

どのような結果が期待できるかをお知らせします: シリアル通信 @ 153K6 ボーレートとスレッド: ステータス ダイオードの点滅、時間管理、要求された関数の評価、IO 処理とロジック、およびすべて atmega328 で。

于 2014-02-02T21:53:35.430 に答える
4

実際のスレッドではありませんが、TimedActions は多くの用途に適した代替手段です

http://playground.arduino.cc/Code/TimedAction#Example

もちろん、1 つのタスクがブロックされると、他のタスクもブロックされますが、スレッドによって 1 つのタスクがフリーズしても、他のタスクは続行されます...

于 2013-12-13T11:50:45.877 に答える
1

前の答えは正しいですが、arduino は一般に非常に高速に実行されるため、コードのタイミングを適切に設定すれば、多かれ少なかれ同時にタスクを実行できます。

ベスト プラクティスは、独自の関数を作成し、デフォルトの void ループに実際のコードを入れすぎないようにすることです。

于 2012-12-22T16:05:02.147 に答える
1

あなたはarduinoを使うことができます

Arduino環境向けに設計されています。特徴:

  • 静的割り当てのみ (malloc/new なし)
  • 実行遅延時のコンテキスト切り替えをサポート
  • セマフォを実装
  • 軽量、CPUとメモリの両方

古いコマンドの実行中に bluetooth/network/serial から新しいコマンドを受信する必要があり、古いコマンドに遅延がある場合に使用します。1 つのスレッドは、次のループを実行するサーバー スレッドです。

while (1) {
    while ((n = Serial.read()) != -1) {
        // do something with n, like filling a buffer
        if (command_was_received) {
            arduinos_create(command_func, arg);
        }
    }
    arduinos_yield(); // context switch to other threads
}

もう 1 つは、コマンドを実行するコマンド スレッドです。

int command_func(void* arg) {
    // move some servos
    arduinos_delay(1000); // wait for them to move
    // move some more servos
}
于 2014-10-02T18:23:08.673 に答える
1

率直な答えは No No No! です。いくつかの代替手段がありますが、Arduino メガから完全なマルチスレッド機能を期待することはできません。以下のように、arduino due または lenado をマルチスレッドに使用できます。

void loop1(){
}
void loop2(){
}
void loop3(){
}

通常、私はそのようなケースをバックエンドで処理します。Arduinoを使用して入力を収集し、出力を表示しながら、サーバーでメインコードを実行できます。そのような場合、wifiが組み込まれているnodemcuを好むでしょう。

于 2020-08-25T12:32:33.853 に答える
1

Arduino はマルチスレッド プログラミングをサポートしていません。

ただし、このプロジェクトのようないくつかの回避策があります (Arduino IDE からもインストールできます)。

実際のマルチスレッド環境では、いつタスクを実行するかを決定するのはOSですが、スケジュール時間を自分で定義する必要があるようです。

または、プロトスレッドを使用できます

于 2018-06-20T10:31:34.977 に答える
0

Arduino はスレッド化をサポートしていません。ただし、次善の策として、インターリーブで実行されているステート マシンを中心にコードを構成することができます。

タスクをステート マシンとして実装する方法はたくさんありますが、このライブラリ ( https://github.com/Elidio/StateMachine ) をお勧めします。このライブラリは、ほとんどのプロセスを抽象化します。

次のようなクラスとしてステート マシンを作成できます。

#include "StateMachine.h"
class STATEMACHINE(Blink) {
  private:
    int port;
    int waitTime;
    CREATE_STATE(low);
    CREATE_STATE(high);

    void low() {
      digitalWrite(port, LOW);
      *this << &STATE(high)<< waitTime;
    }
    void high() {
      digitalWrite(port, HIGH);
      *this << &STATE(low)<< waitTime;
    }
  public:
    Blink(int port = 0, int waitTime = 0) :
      port(port),
      waitTime(waitTime),
      INIT_STATE(low),
      INIT_STATE(high)
      {
        pinMode(port, OUTPUT);
        *this << &STATE(low);
      }
};

マクロSTATEMACHINE()はクラス継承を抽象化し、マクロCREATE_STATE()はステート ラッパーの作成を抽象化し、マクロはINIT_STATE()メソッド ラッピングを抽象化し、マクロSTATE()はステート マシン クラス内のステート ラッパー参照を抽象化します。

状態遷移は、状態マシン クラスと状態の間の演算子によって抽象化され<<ます。遅延状態遷移が必要な場合は、その演算子を整数で使用するだけです。整数はミリ秒単位の遅延です。

ステート マシンを使用するには、まずインスタンス化する必要があります。newセットアップ関数でインスタンス化しながらグローバル空間でクラスへの参照を宣言すると、うまくいくかもしれません

Blink *led1, *led2, *led3;


void setup() {
  led1 = new Blink(12, 300);
  led2 = new Blink(11, 500);
  led3 = new Blink(10, 700);
}

次に、状態をループで実行します。

void loop() {
    (*led2)();
    (*led1)();
    (*led3)();
}
于 2018-11-09T20:06:44.160 に答える