2017-07-08 9 views
3

変数があるので、それを「ID」としましょう。私はこの値を固定量の値と比較して調べる必要があります。もちろん、IDは値の1つにしか一致しないので、他のどれも一致しないので最初の一致する値で停止することに問題はありません。また、変数が指定された値と一致しない可能性もあります。私の質問は、これを行う最もリソース効率的な方法は何ですか?私は問題に取り組む2つの簡単な方法を考えることができます。私は私ができるセットアップ条件付き「または」そのプログラミングの時点で値を知っているので、ちょうどのようなので、それぞれの値をチェックします:ルア - 変数を固定値の値リストと比較する最も効率的な方法

if (ID == "1" or ID == "16" or ID == "58") then 
    --do something-- 
end 

これに伴う問題は、それが書くために非常に冗長と退屈だということです。もう1つのオプションは、あらかじめテーブルを定義するforeachループです。これに

values = {"1", "16", "58"} 
for _, value in ipairs(values) do 
    if(ID == value) then 
     return true 
    end 
end 

逆さま私は、少なくとも10倍の値の異なるセットでこの正確なチェックを行う必要がありますので、それが良いである再利用可能だあり、欠点は、私はそれがより多くのリソースを要する疑いです。

ご協力いただければ幸いです。

答えて

8

テーブルがセットとして使用することができる。

interesting = { 
    ["1"] = true, ["16"] = true, ["58"] = true 
} 

if interesting[ID] then 
    -- ... 
end 

までのエントリの数を丸めながら、エントリ当たりより多くのメモリを(空のテーブルあたり80のバイトとx86_64の上に32バイト(IIRC)(食べながら次の2のべき乗)と比較した16バイトと比較した値の格納と比較して)比較チェーンはC言語で行われるため、Lua命令のシーケンスとしての比較チェーンよりも高速です(少なくとも、 。

値が小さい場合は、これは問題ではありません。 (あなたがCPUにバインドされていて、あなたのケースでこれが非常に重要な場合は、プログラムの文脈でを測定し、より良い結果が得られるかどうかを確認してください。ここで面白い効果が得られます)。

これは正しいアプローチです。 if - then - elseチェーンよりも柔軟です。 (コードをリロードせずに実行時に変更することができます)

また、要素をセットにアンカーするために使用する値は実際には問題にならないので、比較的一般的なイディオム(特に入力処理用)では、テーブルへの関数としてアクション:

keybindings = { 
    left = function() Player:move_left() end, 
    right = function() Player:move_right() end, 
    up = function() Player:jump() end, 
    -- ... 
} 

function onKey(k) 
    local action = keybindings[k] 
    if action then action() end 
end 

これは確かにスピードはここに、本質的に無関係である、直接比較およびインラインコードよりも遅くなります(一般的にあまり多くの場合、毎秒〜の100倍よりも起こる)と柔軟性が高いのですが値。