6

関数定義で引数の長いリストを使用する代わりに、次のようにいくつかの固定パラメーターと「追加パラメーター」のテーブルを渡すことを好みます。

function:doit( text, params )
end

これは、古い呼び出しを中断することなく、後で新しい名前付きパラメーターを追加できるので便利です。

私が経験している問題は、いくつかのパラメータのデフォルト値を強制しようとすると発生します:

function:doit( text, params )
   local font     = params.font or native.systemBold 
   local fontSize = params.fontSize or 24
   local emboss   = params.emboss or true

   -- ...

end

上記のコードは、エンボスに「false」を渡した場合を除いて、すべての場合で正常に機能します。

doit( "Test text", { fontSize = 32, emboss = false } )

上記のコードでは、実際には false が必要なときに emboss が true に設定されます。

明確にするために、私が望むのは、最初の非 NIL 値をエンボスに割り当てることです。代わりに、最初の非 false および非 NIL を取得しています。

この問題に対処するために、テーブル内の最初の非 NIL 値を見つけてそれを返す小さなコードを書きました。

function firstNotNil( ... )
   for i = 1, #arg do
      local theArg = arg[i]
      if(theArg ~= nil) then return theArg end
   end
   return nil
end

この関数を使用して、エンボスの割り当てを次のように書き直します。

   local emboss   = firstNotNil(params.emboss, true)

さて、これは確かに機能しますが、非常に非効率的でやり過ぎのようです。これを行うためのよりコンパクトな方法があることを願っています。

注意してください:有望に見えるこのルビー構造を見つけました。ルアに次のようなものがあることを願っています:

[c,b,a].detect { |i| i > 0 } -- Assign first non-zero in order: c,b,a
4

2 に答える 2

9

Lua の関係演算子は、オペランドの 1 つの値に評価される (つまり、値はブール値に強制されない) ため、C の三項演算子と同等のものを取得できますa and b or c。あなたの場合、そうでない場合とそうでaない場合は使用したいので、次のようにします。nilba == nil and b or a

local emboss = (params.emboss == nil) and true or params.emboss

以前ほどきれいではありませんが、ブール値のパラメーターに対してのみ行う必要があります。


[中略 - Luaコード]

さて、これは確かに機能しますが、非常に非効率的でやり過ぎのようです。

注意してください:有望に見えるこのルビー構造を見つけました。ルアに次のようなものがあることを願っています:

[c,b,a].detect { |i| i > 0 } -- c、b、a の順に最初の非ゼロを割り当てます。

あなたの Lua 関数は、もはややり過ぎでも非効率でもありません。ソース テキストに関しては、Ruby の構造はより簡潔firstNotNil(c,b,a)ですが、セマンティクスは と実際には違いはありません。両方の構成体は、最終的にリスト オブジェクトを作成し、一連の値で初期化し、リストを線形に検索する関数を介してそれを実行します。

Lua では、次のように vararg 式を使用して、リスト オブジェクトの作成をスキップできますselect

function firstNotNil(...)
   for i = 1, select('#',...) do
      local theArg = select(i,...)
      if theArg ~= nil then return theArg end
   end
   return nil
end

これを行うためのよりコンパクトな方法があることを願っています。

これを行う唯一の方法は、関数名を短くすることです。;)

于 2012-07-02T21:50:17.517 に答える