Arduino通過串列埠傳送結構體

2021-07-10 14:16:54 字數 1377 閱讀 7787

arduino的串列埠有兩類傳送的函式serial.print()類和serial.write()類,前者以ascii碼的形式將要傳送的內容編碼傳送,所以我們最後接收並看到的是乙個乙個的ascii碼組合而成的資料,本質上成了字串;後者則以位元組形式直接傳送原始資料,所以我們在串列埠接收工具看到的資料是亂碼,它們在計算機中就是這樣儲存的。

有些時候,我們可能會自己定義資料結構,比如結構體型別的資料。結構體由一些基本的資料型別組合而成,使用者可以自由新增和安排其內容,但是在自己實驗和查閱資料了解到,在微控制器中和在電腦中定義的結構體有一些區別。我們以下面的結構體為例。

typedef struct sdata

sdata;

如果按照arduino的資料型別大小來算,為1+2+4=7,通過sizeof(sdata)驗證後也為7;而如果這個結構體定義在linux作業系統下,用sizeof(sdata)算出來的結果為8,這涉及到計算機位址對齊的問題,具體請參考文章:知道了上面的問題,我們設計結構體就要注意,不同的資料型別順序可能會導致不同的結構體大小,而我們在微控制器如arduino設計結構體時也要考慮對齊問題,比如將上面例子的char定義為二維陣列char c[2],或者把char放到最後,這樣即使我們接收時弄錯了結構體大小,接到的資料也能夠準確的放到結構體中。

在arduino中,print函式和write函式都無法直接傳送結構體資料,因為結構體是使用者自己的定義的,無法像其他資料那樣有固定的格式或大小。所以我們必須將結構體轉為位元組陣列,這樣就可以通過write函式傳送了,下面提供兩種方法實現轉換。

方法一:使用memcpy函式,將結構體中的資料拷貝到乙個位元組陣列中                   

sdata s;

......

byte b[sizeof(sdata)];

memcpy(b,&s,sizeof(sdata));

serial.write(b,sizeof(sdata));

sdata s;

......

byte *tobyte=(byte*)&s;

serial.write(tobyte,sizeof(sdata));

兩種方法在arduino都測試過,都能成功傳送。

接收到這些資料時都是位元組流,一般儲存在緩衝位元組陣列中,如果想轉換成原始的結構體,我們同樣可以用memcpy,用法同上,只是源和目標換了位置。

最後再說一點,如果結構體很大,資料很多,那麼結構體沒有賦值前資料是不確定的,為了避免不確定數帶來的問題,我們該怎麼初始化這個結構體呢?一條一條賦值可以,但是很麻煩。如果要求不高,把結構體內的資料全部置零也算是一種初始化吧,用memset函式可以將目標位址內的資料全部置為指定的資料。不知道還有沒有其他更好的方法,如果有知道的希望能交流交流。

arduino 中斷 串列埠 arduino入門

硬體 arduino uno是基於atmega328p 資料表 的微控制器板。它具有14個數字輸入 輸出引腳 其中6個可用作pwm輸出 6個模擬輸入,工作電壓5v,輸入電壓7 12v。官網的描述 軟體 arduino ide 瀏覽器可以直接搜到 使用 1 安裝arduino軟體一路next就可以,可...

Arduino 串列埠通訊

arduino從基礎到實踐 第三章專案十,因為沒有買藍燈,我用的黃色的led燈代替,如下 char buffer 18 int red,green,yellow int redpin 9 int greenpin 10 int yellowpin 11 void setup void loop wh...

Arduino串列埠通訊

實際上,與arduino開發板進行串列埠通訊非常簡單。在本篇文章中,我們將介紹如何進行溫度測量,然後通過串列埠傳送測量結果。與其他裝置不同,arduino串列埠通訊非常易於使用。串列埠通訊可以是有線或無線的,例如串列埠藍芽連線。arduino程式設計環境有乙個串列埠監視器的工具,專門用於檢視串列埠資...