Does a variable cast back to it's value whenever it's accessed?

Excuse my stupidity but I just wanna know, if for example I store my character (using cast) in a variable within EventBeginPlay, would the cast always be executed when I try to access the variable or does it store a reference to the character directly and won’t be as expensive as using cast every time ?

No, it stores the reference in the variable.

1 Like

A cast is not expensive to begin with so don’t worry.

Depends on the usage… e.g. how often are you casting to the same actor?

Good example would be the animation BP casting to the character class every frame.

That depends: Balancing Blueprint and C++ | Unreal Engine 4.27 Documentation

I would not worry one bit about that. As long as the thing that is Casting to is already loaded it is not expensive at all relatively speaking.

It’s not a big deal if it’s the only instance doing it. But if you have a 64p MP game it gets excessive. Overall it’s just good practice to store a reference for any actor you are going to use frequently.

1 Like

Even though I’ve done this for years, this still gets me at times (because I come from a functional programming background.)

As far as I can tell:
A “variable node” is a reference to the VARIABLE, not to the VALUE of that variable.
A “return slot” from a pure function, is a reference to invoking that pure function.
However, a “return slot” from a function node with sequence connector, is a cache of the value. That cache is valid only for a current synchronous invocation – in an event graph, the return value of one node is not available if the control flow involves some other event or delay node.

Thus, any node with a sequence connector (white control flow) will be calculated only once (when the execution flow gets there,) but any node that’s “pure” will be re-evaluated for each user.

EXCEPT: The “store value to variable” node, has a sequence connector, but re-evaluates the variable each time, because it’s really a combination of a sequenced “store the value” and a pure “read the value” operation.

They could have made this a lot clearer when they started out, if they had done a little more research into previous dataflow and functional programming systems, or, if they did the research, learned some different lessons, but, hey, here we are!

(And even though I think the above are the rules – I may still be getting something wrong. I haven’t seen the semantics of time-of-evaluation and duration-of-cached-value actually written out as a clear rule anywhere. If that exists, please, I’d love to see it!)

3 Likes

The weird thing is you often come across performance questions related to “should I Cast or use a stored reference” and it is hard to even measure the difference between the two.

Meanwhile macros are used everywhere without any thought and they are the real measurable performance killers.

Context of usage, how common said type of usage is utilized across the code base, and how many instances of these cases are in play at any given point is what should be considered.

Casting in of itself isn’t expensive. N casts per frame/tick collectively can be.

That can be said about any function or getter though. Casting isn’t significant enough to require any special attention on how frequently it is called that is my point.

Aren’t Macros just some sort of collapsed nodes that are pasted into the main graph where we’ve placed our Macro? How can they be expensive?

Every single node in a blueprint has a cost that is probably 10x the cost of a simple function call in C++. A macro that contains 10 nodes, would be 100x the cost of a simple function call.
Whether this cost matters, is a different question. If you call it once per ant per step in an ant hill simulation, it will absolutely be. If you call it once per player per tick in a single-player game, it’s unlikely it will matter at all.