This confused me a lot! Can you explain when is the best time to use the dot operator or FindFirstChild()?
Example:
local humanoid = character:FindFirstChild("Humanoid")
--or
local humanoid = character.Humanoid
Which one is better?
This confused me a lot! Can you explain when is the best time to use the dot operator or FindFirstChild()?
Example:
local humanoid = character:FindFirstChild("Humanoid")
--or
local humanoid = character.Humanoid
Which one is better?
Dot operator is faster but will error if the referenced instance does not exist (or hasn’t yet loaded), whereas FindFirstChild() will instead return nil if the instance being referenced either doesn’t exist or hasn’t yet loaded. WaitForChild() will yield (suspend) the current thread’s execution until the referenced instance has loaded (if it exists) otherwise an infinite yield warning will occur.
The dot operator is required for properties of instances as those are properties and not children/descendants, I’d recommend using the dot operator in all circumstances where you know whether or not the instance currently exists/has loaded and then opt to use FindFirstChild() whenever this information isn’t known/isn’t guaranteed.
So, if I have a Part in the workspace, I can use the dot right?
workspace.Part
Yes, that will work providing the part has loaded from the perspective of the script it is being referenced from.
And another example, the player’s character does not exist in the workspace until I start the game. If I wanna get the character’s humanoid, I should do like this right:
local character = workspace:WaitForChild("FSXplay") --FSXplay is the name of my character
local humanoid = character:FindFirstChild("Humanoid")
Or can I use the dot to get the humanoid?
local character = workspace:WaitForChild("FSXplay")
local humanoid = character.Humanoid
Yes and no. FindFirstChild is ~20% slower than the dot operator. (even longer if called with recursion). If your code is heavily performance dependant, you will see a greater benefit out of alternative approaches. Large games need those kinds of optimizations.
That said, most small projects won’t experience the difference with any kind of visual impact.
It’s actually required because you’re indexing information from a userdata valuetype, just as you would index information out of any table.
print(type(workspace.Part)) -- userdata
print(typeof(workspace.Part["Color"])) -- Color3
OP, the only question you need to be asking yourself when deciding between the two is whether or not it makes sense to use. A common malpractice of FindFirstChild is only assessing its result once instead of saving it for later use. You will gain a better understanding of this with more practice and knowledge of Roblox’s engine.
There are very few reasons that you would be manually indexing any normal character controlled Humanoid. You can proceed with Player.CharacterAdded as you see fit instead.
You should see extended usage of FindFirstChild on the client’s end (because instances take time to replicate unless otherwise given NetworkOwnership) when you’re working with game content streaming excessively.
No, I think you should WaitForChild humanoid too because just because the character was made it doesn’t mean the humanoid, character parts, etc were loaded in yet.
Use “.” by default most of the time, if the child fails to be found resulting in an error then that would indicate that the child hasn’t yet loaded and you should use WaitForChild() instead, FindFirstChild() is useful in conditional statements as it can be used to check the existence of something without an error occuring if that thing doesn’t exist.
But if I do that, so when I can use FindFirstChild()?
Generally they are interchangeable I think. I usually use .
but only use it if you’re sure that the Instance is there. Good place to use .
: Getting a part from workspace
Bad place to use .
: getting character and character humanoid
This is true, but as previously stated, one of the biggest pitfalls of learning scripters using FindFirstChild is running on an individual conditional statement that could otherwise be assessed without it. The information returned by FindFirstChild should be used across multiple statements or result in a thread yield. There’s no reason to consistently assess with FindFirstChild, which is benchmarked as slower, if you’re only going to use it once.
So after reading your replies, I have an idea:
local character = workspace:WaitForChild("FSXplay") --FSXplay is the name of the character
then I can get the object’s child/descendant by using the FindFirst method.
local character = workspace:WaitForChild("FSXplay") --FSXplay is the name of the character
local humanoid = character:FindFirstChild("Humanoid")
Simplified:
Is that right?
If you’re expecting it to not exist (like if a key is inserting to the door), use if : FindFirstChild, if you’re expecting it to be there( like mine an object with the default pickaxe), it’s still recommend to use FindFirstChild, but you can also use the dot operator
Alright! Now I’ve understood this, thanks for your replies!