2

キーを持つテーブルと値を持つテーブルの 2 つがあります。それらを結合して、キーと値のペアのテーブルを作成しています。現在、ループを使用しています。より良い方法はありますか?

local keys={"fruit","bread","drink"}
local vals={"apple","french","milk"}

local kv={}
for i=1,#keys do
  kv[keys[i]]=vals[i]
end
4

2 に答える 2

1

オブジェクト指向プログラミング?

-- You could do it in one line too, but this looks neater.
local kv = {fruit = "apple", 
            bread = "french",
            drink = "milk"}

print(kv["fruit"])
print(kv.bread) -- Also works
for index, value in pairs(kv) do --Or you could do it in a for loop
    print("index:", index, "value:", value)
end

あなたは得るでしょう:

apple
french
index:  bread   value:  french
index:  fruit   value:  apple
index:  drink   value:  milk
于 2014-08-04T02:39:22.203 に答える
0

あなたは私のコメントに返信しませんでしたが、とにかくここに答えがあります。

他の人が言ったように、あなたのコードは一般的なユースケースには適しています。特に、後で操作したい場合、kvまたは後で変更される可能性があり、現在の状態のスナップショットであると想定されている場合。keysvalueskv

ただし、特定の状況では、よりエレガントな方法があります。

の唯一の目的が後でそれを反復することである場合(それを操作したり、個々の値を選択したりするのではなく)、次のようkvに で使用できるイテレータを記述できます。for

local keys={"fruit","bread","drink"}
local vals={"apple","french","milk"}:

local function zipkv()
    local i = 0
    return function ()
        i = i + 1
        return keys[i], vals[i]
    end
end


for k,v in zipkv() do
    print("key", k, "value", v)
end

イテレータによって返される関数はkv、最初の戻り値が になるまで、すべての反復の開始時に呼び出されますnil。これには、3 番目のテーブルを作成する必要がないという利点があります。テーブルの代わりにクロージャーを作成していると主張することもできますが、 をkv使用してテーブルを反復処理するpairs場合はpairs、クロージャーを作成する単なるイテレーターでもあります。

もう 1 つの違い (これが利点であるか欠点であるかはユース ケースによって異なります) は、と の現在の状態をzipkv常に反復処理することです。したがって、イテレータを作成した後、イテレータをループで使用する前にそれらを変更する場合は、常に 2 つのテーブルの現在の状態を一緒に圧縮することになります。keysvals

したがって、これは、問題に対するもう少しエレガントな (そしてより効率的な) 解決策があると私が考えることができる 1 つのケースです。しかし、その適用性はいくぶん限定的であるため、「最良の」一般的なアプローチを探していて、すでにそれを見つけているのであれば、私はそう言います.

于 2013-05-05T22:48:20.120 に答える