Main Content

式の畳み込み

式の畳み込みでは、コードを最適化して、ブロック出力での中間結果の計算や、そのような中間結果の一時的なバッファーや変数への保存を最小にします。式の畳み込みがオンのときは、モデル内の個々のブロックに対して別々のコード ステートメントとストレージ宣言を行う代わりに、コード ジェネレーターはブロック演算を単一の式に畳み込みます。式の畳み込みは、ほとんどの Simulink® ブロックでサポートされています。

式の畳み込みは生成コードの効率を高めるため、手動で最適化されたコードに勝る結果を達成することもしばしばあります。多くの場合、モデル計算のすべてのグループを高度に最適化された 1 行のコードに収められます。

モデル例

model = 'FoldBlockComputations';
open_system(model);

コードの生成

式の畳み込みは、ローカル変数を含む式に対してのみ作用するため、[信号ストレージの再利用] パラメーターがオンに設定されている場合にのみ使用できます。[信号ストレージの再利用][余分なローカル変数の削除 (式の畳み込み)] のパラメーターは既定でオンになっています。[余分なローカル変数の削除 (式の畳み込み)] パラメーターをクリアするか、MATLAB® コマンド ウィンドウで次のコマンドを入力してパラメーターをオフにします。

set_param(model, 'ExpressionFolding','off');

モデルを作成します。

slbuild(model)
### Starting build procedure for: FoldBlockComputations
### Successful completion of build procedure for: FoldBlockComputations

Build Summary

Top model targets built:

Model                  Action                        Rebuild Reason                                    
=======================================================================================================
FoldBlockComputations  Code generated and compiled.  Code generation information file does not exist.  

1 of 1 models built (0 models already up to date)
Build duration: 0h 0m 10.366s

式の畳み込みがオフのため、FoldBlockComputations.c ファイルの Switch ブロック演算の前と中に分かれてコード ステートメントがあります。

cfile = fullfile('FoldBlockComputations_grt_rtw','FoldBlockComputations.c');
coder.example.extractLines(cfile,'/* Model step', '/* Model initialize', 1, 0);
/* Model step function */
void FoldBlockComputations_step(void)
{
  real_T rtb_Gain;
  boolean_T rtb_LogicalOperator;
  boolean_T rtb_RelationalOperator;

  /* RelationalOperator: '<Root>/Relational Operator1' incorporates:
   *  Constant: '<Root>/Constant'
   *  Inport: '<Root>/In2'
   */
  rtb_LogicalOperator = (FoldBlockComputations_P.UPPER >=
    FoldBlockComputations_U.In2);

  /* RelationalOperator: '<Root>/Relational Operator' incorporates:
   *  Constant: '<Root>/Constant1'
   *  Inport: '<Root>/In2'
   */
  rtb_RelationalOperator = (FoldBlockComputations_U.In2 <=
    FoldBlockComputations_P.LOWER);

  /* Logic: '<Root>/Logical Operator' */
  rtb_LogicalOperator = (rtb_LogicalOperator || rtb_RelationalOperator);

  /* Switch: '<Root>/Switch' */
  if (rtb_LogicalOperator) {
    /* Gain: '<Root>/Gain' incorporates:
     *  Inport: '<Root>/In1'
     */
    rtb_Gain = 2.0 * FoldBlockComputations_U.In1;

    /* Lookup_n-D: '<Root>/Look-Up Table' incorporates:
     *  Gain: '<Root>/Gain'
     */
    rtb_Gain = look1_binlx(rtb_Gain, FoldBlockComputations_P.T1Break,
      FoldBlockComputations_P.T1Data, 10U);
  } else {
    /* Lookup_n-D: '<Root>/Look-Up Table (2-D)' incorporates:
     *  Inport: '<Root>/In3'
     *  Inport: '<Root>/In4'
     */
    rtb_Gain = look2_binlx(FoldBlockComputations_U.In3,
      FoldBlockComputations_U.In4, FoldBlockComputations_P.T2Break,
      FoldBlockComputations_P.T2Break, FoldBlockComputations_P.T2Data,
      rtCP_LookUpTable2D_maxIndex, 3U);
  }

  /* End of Switch: '<Root>/Switch' */

  /* Outport: '<Root>/Out1' */
  FoldBlockComputations_Y.Out1 = rtb_Gain;
}

最適化を使用したコードの生成

次のコマンドを入力して式の畳み込みをオンにします。

set_param(model, 'ExpressionFolding','on');

モデルを作成します。

slbuild(model);
### Starting build procedure for: FoldBlockComputations
### Successful completion of build procedure for: FoldBlockComputations

Build Summary

Top model targets built:

Model                  Action                        Rebuild Reason                   
======================================================================================
FoldBlockComputations  Code generated and compiled.  Generated code was out of date.  

1 of 1 models built (0 models already up to date)
Build duration: 0h 0m 7.0506s

以下は FoldBlockComputations.c の一部です。この最適化されたコードでは、コード ジェネレーターですべての計算が Switch ブロック演算に畳み込まれています。

coder.example.extractLines(cfile,'/* Model step', '/* Model initialize', 1, 0);
/* Model step function */
void FoldBlockComputations_step(void)
{
  /* Switch: '<Root>/Switch' incorporates:
   *  Constant: '<Root>/Constant'
   *  Constant: '<Root>/Constant1'
   *  Inport: '<Root>/In2'
   *  Logic: '<Root>/Logical Operator'
   *  RelationalOperator: '<Root>/Relational Operator'
   *  RelationalOperator: '<Root>/Relational Operator1'
   */
  if ((FoldBlockComputations_P.UPPER >= FoldBlockComputations_U.In2) ||
      (FoldBlockComputations_U.In2 <= FoldBlockComputations_P.LOWER)) {
    /* Outport: '<Root>/Out1' incorporates:
     *  Gain: '<Root>/Gain'
     *  Inport: '<Root>/In1'
     *  Lookup_n-D: '<Root>/Look-Up Table'
     */
    FoldBlockComputations_Y.Out1 = look1_binlx(2.0 * FoldBlockComputations_U.In1,
      FoldBlockComputations_P.T1Break, FoldBlockComputations_P.T1Data, 10U);
  } else {
    /* Outport: '<Root>/Out1' incorporates:
     *  Inport: '<Root>/In3'
     *  Inport: '<Root>/In4'
     *  Lookup_n-D: '<Root>/Look-Up Table (2-D)'
     */
    FoldBlockComputations_Y.Out1 = look2_binlx(FoldBlockComputations_U.In3,
      FoldBlockComputations_U.In4, FoldBlockComputations_P.T2Break,
      FoldBlockComputations_P.T2Break, FoldBlockComputations_P.T2Data,
      rtCP_LookUpTable2D_maxIndex, 3U);
  }

  /* End of Switch: '<Root>/Switch' */
}

モデルおよびコード生成レポートを閉じます。

bdclose(model)