8

質問の無関係な正当化:

Lua の呼び出しでエラーが発生しましたformat:

-1.#IND を格納しようとする整数オーバーフロー

変数はtype(n)実際にはであり、文字列 (つまり ) として指定numberできますが、数値ではありません。たとえば、次のようになります。format%s

print(string.format("value=%s, type=%s", n, type(n)));

NaN戻り値は次のとおりです。

値=-1.#IND、タイプ=数値

これを修正したいのですが、誰がこれを生成しNaNているのかわかりません (Lua にはデバッガーがありません)。

したがってasserts、この断続的な値の原因を突き止めることができるまで、コード全体に多くのことをスローする必要がありNaNます。

しかし、私はそれをトラップする条件を見つけることができず、Lua にはありませんisnan(x)

質問:

-1.#INDLuaで数値をテストするにはどうすればよいですか?

更新

私は試した:

if (n ~= n) then
   print(string.format("NaN: value=%s, type=%s", n, type(n)));
else
   print(string.format("value=%s, type=%s", n, type(n)));
end;

そしてそれは印刷します

値=-1.#IND、数値

更新 2 : 念のため、何かを見逃した場合に備えて、実際のコードは次のとおりです。

    if (oldValue ~= oldValue) then
        print(string.format("Is NaN: labelNumber=%d, formatString=\"%s\", oldValue=%s (%s)", labelNumber or 0, formatString or "nil", oldValue or "nil", type(oldValue)));
    else
        print(string.format("Is not NaN: labelNumber=%d, formatString=\"%s\", oldValue=%s (%s)", labelNumber or 0, formatString or "nil", oldValue or "nil", type(oldValue)));
    end;

そして、誤った値が出力されます:

NaN ではない: labelNumber=4、formatString="%d"、oldValue=-1.#IND (数値)

アップデート 3

まだこの問題を解決しようとしているのですが、現実の不条理に気づきました:

function isnan(x)
   if type(x) ~= "number" then
       return false; --only a number can not be a number
   end;

   ...
end;
4

3 に答える 3

4

n ~= n動作する可能性があります(マッドの回答で説明されている警告があります)が、より移植性の高いものは次のとおりです。

function isnan(n) return tostring(n) == tostring(0/0) end

ゼロ除算が気になる人は (Ian のコメントのように、実際には見たことがありませんが)、代替バージョンを使用できます。

function isnan(n) return tostring(n) == tostring((-1)^.5) end

フル機能:

--local nanString = (tostring((-1) ^ 0.5)); --sqrt(-1) is also NaN. 
--Unfortunately, 
--  tostring((-1)^0.5))       = "-1.#IND"
--  x = tostring((-1)^0.5))   = "0"
--With this bug in LUA we can't use this optimization
local function isnan(x) 
    if (x ~= x) then
        --print(string.format("NaN: %s ~= %s", x, x));
        return true; --only NaNs will have the property of not being equal to themselves
    end;

    --but not all NaN's will have the property of not being equal to themselves

    --only a number can not be a number
    if type(x) ~= "number" then
       return false; 
    end;

    --fails in cultures other than en-US, and sometimes fails in enUS depending on the compiler
--  if tostring(x) == "-1.#IND" then

    --Slower, but works around the three above bugs in LUA
    if tostring(x) == tostring((-1)^0.5) then
        --print("NaN: x = sqrt(-1)");
        return true; 
    end;

    --i really can't help you anymore. 
    --You're just going to have to live with the exception

    return false;
end
于 2012-08-24T04:23:30.853 に答える
1

Lua には isnan(x) がありません。

Lua ホストに追加するか、その機能を備えたモジュールを作成できます。ほんの数行のコードです。

Luaで-1.#INDの数値をテストするにはどうすればよいですか?

NaN を文字列表現 に変換していることがわかる'-1.#IND'ので、次のように記述できます。

function isnan(n) return tostring(n) == '-1.#IND' end

または、プラットフォーム、コンパイラ、コンパイラの設定などに応じて、これは機能します。

function isnan(n) return n ~= n end
于 2012-08-24T04:13:13.457 に答える
0

シリアル化の目的では、これが私にとって最もうまくいくようです:

local function isnan(val)
    if val==1/0 then return "1/0"
    elseif val==-1/0 then return "-1/0"
    elseif val~=val then return "0/0"
    end
end

これにより、次のことが可能になります。

print(v .. " = " .. isnan(val) or val)

結果は、たとえば、次のようになります。

{
  foo = 1/0,
  bar = 0/0,
  bla = -1/0,
}
于 2014-04-09T23:37:49.000 に答える