# TWEFMT

書式を解釈して得られたデータ列は、受信したパケット情報が含まれます。ここでは、このデータ列のことをパケットデータと呼びます。

パケットデータは[`TwePacket`](https://mwm5.twelite.info/1.0-2/references/parser/twefmt/twepacket)クラスで表現されます。`TwePacket`クラスのデータを解釈することで、その種別を判定し、各アプリケーションや接続ハードウェアに応じたデータ構造となります。`TwePacket`クラスは基底クラスでさらにパケット種別ごとの派生クラスとなります。

このオブジェクトは無線パケットのデータ量に準じたメモリ領域を消費し、また、アプリケーションでは多数のパケットを保持することも考えられます。メモリ管理を簡略化するため`TwePacket`をスマートポインタ`std:shared_ptr<TwePacket>`にて管理します。このスマートポインタを`spTwePacket`に`typedef`しています。

以下に、TWELITE PALのパケットデータの場合のクラス関係を示します。`TwePacketPal`の基底クラスの一つ`DataPal`はTWELITE PAL特有のデータを格納しています。TWELITE PALには、さらに接続されるセンサーパルによって格納すべきデータが異なります。`TwePacketPal`からさらに`PalAmb`や`PalMot`を生成します。例えば`PalAmb`には温室センサーの値や照度センサーの値が格納されます。この`TwePacketPal`をスマートポインタ`spTwePacket`という形に生成するのが`newTwePacket()`です。

```
    [spTwePacket] ←(生成)- newTwePacket()
          ◆ 
          ｜(shared_ptr)
          ｜
      [TwePacket]    [DataPal]
              ↑        ↑
            [TwePacketPal] -(生成)-> [PalAmb], [PalMot], ...
```

`spTwePacket`型はスマートポインタですので、オブジェクトのコピー渡しによる記述を行うことで、コピーのオーバーヘッドを最小にしつつ、メモリーの管理を自動化できます。以下の例はパケットの履歴を管理する単純なクラスです。

```cpp
struct _pkt_hist {
	spTwePacket _pkt[16]; // パケットの履歴
	int _i;

	_pkt_hist() : _i(-1), _pkt{} {}
	void add_entry(spTwePacket p) { _pkt[++_i & 0xF] = p; }
	spTwePacket get_entry(int i) { return _pkt[(i + _i) & 0xF]; }
} pkt_hist;

void loop() {
  spTwePacket pkt, pkt_last;
  
  // 新たなパケットオブジェクト
  pkt = newTwePacket(p, len);
  pkt_hist.add_entry(pkt); // 履歴に保存する

  // ひとつ前のパケットオブジェクト
  pkt_last = pkt_hist.get_entry(-1);
}
```
