Scripting Helpers is winding down operations and is now read-only. More info→
Ad
Log in to vote
2

bad argument #1 to 'gsub' (string expected, got user data), why?

Asked by
thePyxi 179
9 years ago

This script is to add commas in the number for cash, yet it always returns as a bad argument.

Here's the code:

function addComma(n)
    local f,k = n
    while (true) do
        f,k = string.gsub(f,"^(-?%d+)(%d%d%d)","%1,%2")
        if (k == 0) then break end
    end
    return f
end

It breaks on line 4 saying: bad argument #1 to 'gsub' (string expected, got userdata)

Can someone help me with this?

This is the entire code, which is inside a TextLabel

wait(1.2)

local plr=script.Parent.Parent.Parent.Parent.Parent
local stats=plr:FindFirstChild('leaderstats')
local dollars2=stats:FindFirstChild('Money')


function addComma(n)
    local f,k = n
    while (true) do
        f,k = string.gsub(f,"^(-?%d+)(%d%d%d)","%1,%2")
        if (k == 0) then break end
    end
    return f
end

function force_decimal_places(num, places)
    if type(num) ~= 'number' or type(places) ~= 'number' then
        return 'NaN' --not a number
    end
    local mult = 10^(places or 0) --set up rounding places
    num = tostring( math.floor(num * mult + 0.5) / mult ) --round
    local dot = string.find(num, '%.')
    if not dot then --easily add zeros to an integer
        num = num..'.'..string.rep('0', places)
    else --some after decimal?
        local after = string.sub(num, dot + 1)
        if after ~= places then --if it doesn't already round to exact places
            num = num..string.rep('0', places - #after)
        end
    end

    return num --returns a string (otherwise the zeros would get truncated)
end

while wait(0.1) do
    dollars2 = addComma(dollars2)
local dollars = force_decimal_places(dollars2.Value, 2)
script.Parent.Text = '$'..dollars 
end

2 answers

Log in to vote
2
Answered by
adark 5487 Badge of Merit Moderation Voter Community Moderator
9 years ago

If you try to set dollars2 to the value returned by addComma, you lose the reference to the Money ValueObject, breaking the script.

addComma expects a string. First, you set f = n on the first line. Then, you call gsub on f. If f isn't a string, this doesn't work.

Additionally, force_decimal_places expects a number, since you perform math on it. To fix these, you need to change your loop:

while wait(.1) do
    local dollars = force_decimal_places(dollars2.Value, 2)
    dollars = addComma(dollars)

    script.Parent.Text = "$" .. dollars
end

Or, more compactly and efficiently:

function fixText()
    script.Parent.Text = "$" .. addComma(force_decimal_places(dollar2.Value, 2))
end
dollars2.Changed:connect(fixText)
fixText()
Ad
Log in to vote
1
Answered by
BlueTaslem 18071 Moderation Voter Administrator Community Moderator Super Administrator
9 years ago

f is dollars, since that's the parameter you passed. dollars2 is a userdata, as it says. That means it's a ROBLOX object.

Instead, use addComma( tostring(dollars2.Value) ) to get the value of that object, and apply string processing to it. I'm unsure why you'd overwrite the dollars2 variable with that string, though, since that will prevent the value from updating in the future.

0
The line breaks at the 4th line of function addComma(n) thePyxi 179 — 9y
0
Yes, because `f` is `n` which is `dollars2`. You should instead call it with `tostring(dollars2.Value)` so that `n` and `f` are strings. BlueTaslem 18071 — 9y

Answer this question