Scripting HelpersARCHIVE
A little piece of Roblox history. Preserved for everyone, one question at a time.Read about the archive →
✓ ANSWER ACCEPTED

Is there a better way to check if a value is not equal to another value?

I have this value that it inside the player and I want the dataStore to update every time the value changes. I don't think I'm doing it right on line eight. The script runs without any errors, but it won't work.

local DataStore = game:GetService("DataStoreService"):GetDataStore("Cash")

while true do
     wait(1)
	game.Players.PlayerAdded:connect(function(player)
	local v = player.Value.Value
	local key = "user_" ..player.userid
	if DataStore:GetAsync(key) == v == nil then 
		DataStore:UpdateAsync(key, function(oldValue)
		local newValue = oldValue or 0 
		newValue = v
		return newValue
	end)
	end
	end)
end

1 answer

✓ Accepted answer

You are connecting a PlayerAdded event to your function every second. If a player joins after 60 seconds, this means that your function will run 60 times!

Fortunately, we don't need the loop at all -- just listen for the Changed event.

local DataStore = game:GetService("DataStoreService"):GetDataStore("Cash")
game.Players.PlayerAdded:connect(function(player)
	local key = "user_" ..player.userid
	local v = player:WaitForChild("Value") --I will assume that this 'value' is the Cash Int/NumberValue and that v.Value is the actual amount of cash
	v.Value = DataStore:GetAsync(key) or 0
	v.Changed:connect(function()
		DataStore:UpdateAsync(key, function(oldValue)
			if oldValue == v.Value then return end --returning nil cancels the update
			return v.Value
		end)
	end)
end)

However, according to the API, datastores may error unexpectedly, which is why I recommend wrapping calls to the datastores in pcall. I've written a small function, "Try10", which will attempt to run a function up to 10 times before giving up. The full script:

local DataStore = game:GetService("DataStoreService"):GetDataStore("Cash")
function Try10(Func) --Tries to perform Func up to 10 times, returning the results of pcall
	local success, message
	for i = 1, 10 do
		success, message = pcall(Func)
		if success then return success, message end
		wait(0.1)
	end
	return success, message
end
game.Players.PlayerAdded:connect(function(player)
	local key = "user_" ..player.userid
	local v = player:WaitForChild("Value") --I will assume that this 'value' is the Cash Int/NumberValue and that v.Value is the actual amount of cash
	local success, message = Try10(function()
		v.Value = DataStore:GetAsync(key) or 0
	end)
	if not success then warn("Unable to load cash value from datastores: " .. tostring(message)) end
	v.Changed:connect(function()
		local success, message = Try10(function()
			DataStore:UpdateAsync(key, function(oldValue)
				if oldValue == v.Value then return end --returning nil cancels the update
				return v.Value
			end)
		end)
		if not success then warn("Unable to save cash value to datastores: " .. tostring(message)) end
	end)
end)

2 comments

0

Thank you! I have never had a better and most straightforward answer before.

0

Ah, yes, I remember when I first discovered the Changed event. It's a really useful one for things like this.

This discussion is preserved as it was. New answers, comments, and votes are closed.