この初版はLua 5.0のために書かれました。後続のバージョンでも依然として関連性は高いものの、多少相違があります。
第4版はLua 5.3を対象にしており、Amazonおよびその他の書店で購入できます。
本を購入することで、Luaプロジェクトの支援にも役立ちます。
![]() |
Programming inLua | ![]() |
| 第 1 部: 言語 第 5 章: 関数 |
Luaの一部の関数は可変長引数を受け取ります。たとえば、printを1つ、2つ以上などの引数で呼び出しています。
ここで、Luaでprintを再定義するとします。恐らく私たちのシステムにはstdoutがなく、その結果、printは引数を後で使用するためにグローバル変数に格納するのではなく、それらの引数を印刷します。この新しい関数をLuaで次のように記述できます。
printResult = ""
function print (...)
for i,v in ipairs(arg) do
printResult = printResult .. tostring(v) .. "\t"
end
printResult = printResult .. "\n"
end
パラメータリストにある3つのドット(...)は、関数が可変長引数を持つことを示します。この関数が呼び出されると、そのすべての引数が単一テーブルに収集され、関数は隠れたパラメータargとしてこれにアクセスします。これらの引数に加えて、argテーブルには、収集された引数の実際数を表す追加フィールドnがあります。場合によっては、関数は固定パラメータに加えて可変長パラメータを持つことがあります。例を見てみましょう。式に複数の値を返す関数を記述する場合、その最初の結果のみが使用されます。しかし、場合によっては別の結果が必要になります。一般的な解決策はダミー変数を使用することです。たとえば、string.findから2番目の結果のみが必要な場合、次のコードを記述できます。
local _, x = string.find(s, p)
-- now use `x'
...
もう1つの解決策は、関数から特定のリターンを選択するselect関数を定義することです。 print(string.find("hello hello", " hel")) --> 6 9
print(select(1, string.find("hello hello", " hel"))) --> 6
print(select(2, string.find("hello hello", " hel"))) --> 9
selectの呼び出しは常に1つの固定引数(セレクタ)と、可変長追加引数(関数の戻り値)を持つことに注意してください。この固定引数を収容するため、関数はドットの前に通常の引数を持つことができます。その後、Luaは最初の引数をそれらパラメータに代入し、それ以外の引数(ある場合)のみをargに代入します。この点をより明確にするために、次のような定義があるとします。function g (a, b, ...) endその場合、次の引数のパラメータへのマッピングがあります。
CALL PARAMETERS
g(3) a=3, b=nil, arg={n=0}
g(3, 4) a=3, b=4, arg={n=0}
g(3, 4, 5, 8) a=3, b=4, arg={5, 8; n=2}
それらの通常の引数を使用して、selectの定義は簡単です。
function select (n, ...)
return arg[n]
end
可変長引数を持つ関数は、それらをすべて別の関数に渡す必要がある場合があります。唯一行う必要があるのは、引数としてunpack(arg)を使用して別の関数を呼び出すことです。unpackはargのすべての値を返します。これは別の関数に渡されます。この使用の良い例は、書式付きテキストを記述する関数です。Luaには、テキストの書式を指定する個別関数(string.format。Cライブラリのsprintf関数と同様)と、テキストを記述する関数(io.write)があります。もちろん、この2つの関数を1つの関数に簡単に結合できます。この新しい関数は、可変長の値をformatに渡す必要があるという点を除いてです。これはunpackの仕事です。
function fwrite (fmt, ...)
return io.write(string.format(fmt, unpack(arg)))
end
| Copyright © 2003–2004 Roberto Ierusalimschy. All rights reserved. | ![]() |