繰り返さないループで内部状態を保持 のバックアップ差分(No.3)

更新


  • 追加された行はこの色です。
  • 削除された行はこの色です。
[[公開メモ]]

* 概要 [#cf353635]

繰り返さないループで内部状態を保持するというテクニックを使うと、
通常通りにシフトレジスタを使った場合にはロジックが入り組んでしまい、
サブVI 化しにくいようなデザインからサブVIを切り出して見やすくできる場合があります。

下記のブロックダイアグラム画像はVIスニペットになっているので、
画像を LabView へドロップすると、簡単に試せます。→ [[プログラミング/LabView/VIスニペット]]

* 入力値が変更されたことを検出するには [#d52d127c]
* 例:入力値が変更されたことを検出するには [#d52d127c]

普通こんな風にするのではないかと思います。

&attachref(detect_change.png);

フロントパネルはこう。

&ref(detect-change-frontpanel.png);

数値を変更すると、「変更された」のランプが光ります。

動作的には、

- 前回の値をループのシフトレジスタに保存する
- 前回の値と今回の値が異なればランプを光らせる

という形です。

** ループをまたぐ線が邪魔 [#v2208d57]

ループの端から端まで線が延びるので、ダイアグラムがごちゃごちゃします。

** サブ VI として切り出せない [#xc940ce9]

上の形だと「変更を検知する」という機能をサブVIとして切り出すことができません。
* 繰り返さないローカルループを使って書き換える [#l5c31449]

下記の回路は上記と同じ動作をします。

&attachref(detect_change2.png);

フロントパネルは同じです。

- 内側のループの繰り返し条件は False なので1度しか実行しない、繰り返さない「ループ」になっている
- このループのシフトレジスタに、前回の値を保存する
- 保存した値はループへ再入した際に使えるため、このシフトレジスタは「ローカル変数」のような働きをする
- 初回はシフトレジスタに値が入っていないので読まないようにする

外側ループの端から端まで伸びる線がなくなって、かなりすっきりします。

この形であれば内側ループ部分をサブVI化できるので、

&ref(detect-change3.png);

こうしてしまえばとても見やすいです。

* 応用例1:IIR ローパスフィルタ [#l3194342]

入力値にローパスフィルタを掛けた値を出力します。

前回の出力の値をシフトレジスタに保存しています。

&attachref(iir-lowpass.png);

&ref(iir-lowpass-frontpanel.png);

&attachref(iir-lowpass.gif);

* コメント・質問 [#a656371b]

#article_kcaptcha



Counter: 7208 (from 2010/06/03), today: 1, yesterday: 0