Object Lifetime in C++ (Stack/Scope Lifetimes)
Key Takeaways
The video discusses object lifetime in C++, focusing on stack and scope lifetimes, and demonstrates how to manage memory using scoped pointers and automatic resource management.
Full Transcript
hey what's up guys my name is the churner and welcome back to my stay plus plus series I need a haircut so today I'm gonna be talking all about objects lifetimes I'm gonna kind of start talking about memory and how objects live specifically on these stack I am going to make a heat versus tack video in which we can actually talk about this stuff in depth as well as probably benchmark the difference in terms of performance and just talk about all the performance kind of metrics and and and all that kind of stuff in that video but today we're just gonna this is like a gentle introduction to what lifetime kind of means for stack-based variables so there's kind of two parts to this this this the first part is kind of you have to understand how things live on the stack in order for you to actually be able to write code that doesn't crash and code that works but also this actor set the next step once you know how this works is that I now know how to leverage this and make it kind of do what I wanted to do and come up with clever ways to do things and we'll talk about well we'll look at some examples of what I mean by that today but basically we have this concept of stacks how two stacks well we'll have a web of video in depth about that I know that I keep saying we'll have a video for pretty much every topic but it's just I don't want to focus on the details of certain elements in every video because otherwise these videos we've 45 minutes not helpful to people who already know that stuff that's why I'm kind of trying to monetize this series the best thing a stack can be thought of as a data structure in which you stack things on top pretend that you've got a stack of books on your desk in order for you to actually access one in the middle you would have to take the first few off to get to that that book in the middle of course in real life you could just yank it out but that's not how stacks work in programming so every time we enter a scope in C++ we basically push us push stack frame on it doesn't necessarily have to be a stack frame in the case of I'm actually pushing data on but you can think of it as adding a book to your pile and any variables that you declare inside that scope is like writing stuff into your book and once that scope ends and you take that book off of your pile of books it's gone right every stack based variable which you declared in that book every object that you created on the stack inside that book they're gone now and that is both a blessing and a curse but if you know what you're doing then obviously it's just be a blessing 100% of the time right so I'm going to show you some examples of exactly how all of this comes together and how all this works and hopefully doesn't make it painfully obvious to you so first of all let's talk about scopes a scope can be anything from a function scope like what this is right here some kind of if statements cope like this or could also be in a for loop or a while loop or just an empty Scott like that we also have scopes for classes meaning that when I declare a class like entity it's my go-to example and I have some kind of stack initialized variable here so something that isn't allocated on the heap here then this variable is also inside this class scope meaning that when this class dies this variable dies so let's see this in action I'm going to just write a very simple entity class here this doesn't have to be an empty class could be absolutely anything it's going to have a constructor here which is going to print something to the console like create identity and we're also going to give this class a destructor I'm actually just going to copy this add the tilde here to make it a destructor and change this to destroyed entity so we have created entity in a constructor and destroyed entity in a destructor inside this scope over here I'm going to declare my entity instead of creating it on the heap on guard credit on the stack just by writing code like star this is going to call the default constructor I'm going to put a breakpoint on this line and hit f5 to run my program okay so once I hit this breakpoint I'm just going to open my console here so that we can see what's happening if I hit f10 to advance one line forward you'll see the creative entity gets printed to the console now we are at the end of this scope here so as soon as I hit f10 we are destroying our entity that entity is gone now that memory has been freed should be pretty obvious if I was to do a heap allocation on this by converting this into a pointer and writing code like so with optional parentheses if I hit f5 here I'll have one line of code forward and you can see that we didn't even go to the scope here if I look at my console we just say credit entity and that's it we're already on this line I can even execute this line so right now we're actually waiting for input and you can see our entity never gets destroyed of course that memory does get cleaned up by the operating system when our application terminates so straight away you should see the difference in object lifetimes between a stack-based variable and a heat-based variable based variable gets freed gets destroyed as soon as we go out of scope so that's basically the point of today's video I just want you to get it into your head that if you declare something on the stack if you create a variable on the stack it's going to cease to exist when it goes out of start now let's take a look at some things you might not want to do now that you have this knowledge a great example is I want to create an array inside a function maybe it's an integer array so it will return an int pointer I'll call this create array and I might write code such as int array so this is going to allocate the array 15 here to just large and then I can return a raid now this looks like perfectly sensible card I mean is creating an array and then returning a pointer to that array seems legit right wrong you're completely wrong if you thought that was legit I really hope you did let's take a look at why so by creating an array like this we're not allocating on it on the heap we're not calling new or doing some kind of heap allocation we are just declaring it on the stack and when we return a pointer to that is returning a pointer to that stack memory guess what that stack memory gets cleared as soon as we go out of scope so if you write code like this it's going to fail if you would like to write a function like this you basically have two options you can either get this to actually allocate the array on the heap thus ensuring that its lifetime will actually stay around or you could ask this data that you've created here to actually be copied to a location that exists further up the stack so it has an example let's say I actually create my array over here of 50 integers and then I want this credit ready to be more of a fill array which would take in that array as a parameter and actually do anything that it had to do here of course this example of creating an array kind of falls apart since when I love are creating it inside here but we are still basically manipulating it so maybe this could do something like fill our array and in this sense we're just passing a pointer so it's not going to get de-allocated that array creation is a classic mistake which I actually tend to say all the time people will create a stack based variable and try to return a pointer to it no realizing that once that function ends and you go out of scope that variables done so with this kind of automatic destruction of stack based variables is there a way that we can kind of make it useful is there a way that we can leverage it and use it for good and the answer is yes there are plenty of ways in which this is incredibly useful and can actually help kind of automate code and one thing that we can do with this is actually write scoped kind of classes right such as a smart pointer like unique pointer which is a scoped pointer or something like a scoped lock that there's a lot of examples which we will definitely get into in the future but the simplest example is probably a stroked pointer what that basically is is a class that's a wrapper over a pointer which upon construction heap allocates the pointer and then upon destruction deletes the pointer so we can kind of automate this new and delete thing let's take a look at how we might write a class like that so this entity right I want to still allocated on the heap I want to call new and all that however I wanted to automatically be deleted when this goes out of scope can we do that the answer is yes so we could use something in the standard library called a unique pointer which is a scoped pointer but for the purposes of this example we'll write our own so that you can see how it works I write a class called scarf 2.0 I'm going to keep it really simple for now and just hog credit to only accept entities so this will be our actual pointer upon construction I'm going to write a constructor which takes in our entity so this is an MC point up I'm going to assign s to here and upon destruction I'm going to call delete and point up just like that and that's it that is a basic scoped pointer so let's take a look at how we can use that instead of writing entity a equals new entity I'm actually going to ride scoped pointer E which is basically our variable name equals new entity I could have also written this like so with the default constructor but just to keep it similar to what it was before it kind of looks the same and of course this works due to implicit conversion so this kind of looks like identical code but the difference is that this will actually get destroyed once we go out of scope because of course the scoped pointer class itself the scoped pointer object gets allocated on the stack which means that it gets deleted and when it gets deleted automatically equals delete in the destructor which deletes that that pointer that it's wrapping so if we put a breakpoint here and hit f5 will advance one line forward check our console we see we can see the work-ready mantasy and then one line forward again and check this out we destroyed our entity even though we use new to heap-allocated and that is a great example of first of all what a very basic smart pointer called unique pointer does we're going to have an entire video dedicated to smart pointers various you know people have been like people have been complaining about me using new and not using smart pointers and teaching bad C++ we're gonna have a real little chat about that later by the way but for all of you waiting for smart pointers we're definitely gonna do a video on that very very soon because they're a very important part of the language so this kind of automatic creation an automatic destruction that we can kind of get from the fact that a stack based variable goes out of scope and gets destroyed is actually really useful and there are plenty there are plenty of more examples just to name another one off the top of my head a timer let's just say you wanted time how long you are inside a scope for benchmarking or something you could write a time a class which starts the timer upon construction of the object and that stops the time I maybe prints the result or whatever when the object when the timer object gets destroyed so suddenly you've got an automatic timer you just write one line of code at the beginning of your function and that entire scope is going to now be timed and you turn and you never have to call time it'll stop or whatever manually because as soon as it goes out of scope and calls that for you automatically it's really amazing and there's so many uses for it another one is mutex locking if you want to lock a function so the multiple threads can't access it at the same time and caused an explosion you can have an automatic scoped lock which at the beginning of the function locks it and at the end of the function unlocks it and the Reds are coming soon I really can't wait to get into the more kind of complicated and fun stuff in C++ so don't you worry many more videos are coming hope you guys enjoyed this video if you did you hit that like button I think is in that corner I will always pointing over there and all the other videos but I think it's here so now that you know where it is you can click it you can also help support this series on patreon by going to patreon at home for sash the churner there's plenty of cool rewards that you can get access to such as a private discord chat where we plan these videos you can request whatever you like you can ask me any questions you want there as well and I of course I I of course answer all of my patrons because why wouldn't I but the most important thing you do by supporting is just making sure that I can make more of these videos and get them out as fast as possible so a huge thank you to all of my supporters on that I will see you guys next time I think next time we're gonna finally talk about smart pointers because well yeah I'll see you guys next time goodbye [Music]
Original Description
Patreon ► https://patreon.com/thecherno
Twitter ► https://twitter.com/thecherno
Instagram ► https://instagram.com/thecherno
Discord ► https://discord.gg/R2t97wf
In this video we'll be talking about lifetimes in C++. This specifically refers to how long stack allocated variables will actually last for; that is, how long will their memory be "alive" until it automatically gets freed and cleaned up.
Series Playlist ► https://www.youtube.com/playlist?list=PLlrATfBNZ98dudnM48yfGUldqGD0S4FFb
Thank you to the following Patreon supporters:
- Samuel Egger
Gear I use:
-----------------
BEST laptop for programming! ► http://geni.us/pakTES
My FAVOURITE keyboard for programming! ► http://geni.us/zNhB
FAVOURITE monitors for programming! ► http://geni.us/Ig6KBq
MAIN Camera ► http://geni.us/t6xyDRO
MAIN Lens ► http://geni.us/xGoDWT
Second Camera ► http://geni.us/CYUQ
Microphone ► http://geni.us/wqO6g7K
Watch on YouTube ↗
(saves to browser)
Sign in to unlock AI tutor explanation · ⚡30
Playlist
Uploads from The Cherno · The Cherno · 0 of 60
← Previous
Next →
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
3D Game Programming - Episode 1 - Window
The Cherno
3D Game Programming - Episode 2 - Game Loop
The Cherno
3D Game Programming - Episode 3 - Arrays
The Cherno
3D Game Programming - Episode 4 - Drawing Pixels!
The Cherno
3D Game Programming - Episode 4.5 - How Rendering Works
The Cherno
3D Game Programming - Episode 5 - Playing with Pixels!
The Cherno
3D Game Programming - Episode 6 - Performance Boosting
The Cherno
3D Game Programming - Episode 7 - FPS Counter
The Cherno
3D Game Programming - Episode 8 - Alpha Support and More
The Cherno
3D Game Programming - Episode 9 - Beginning 3D
The Cherno
3D Game Programming - Episode 10 - Floors and Animation
The Cherno
3D Game Programming - Episode 11 - Rotation
The Cherno
3D Game Programming - Episode 12 - User Input
The Cherno
3D Game Programming - Episode 13 - Render Distance Limiter!
The Cherno
3D Game Programming - Episode 14 - Basic Mouse Movement
The Cherno
3D Game Programming - Episode 15 - Textures + More!
The Cherno
3D Game Programming - Episode 16 - Walking, Crouching, Sprinting + More
The Cherno
3D Game Programming - Episode 16.5 - Exporting Runnable Jars
The Cherno
3D Game Programming - Episode 17 - Small Adjustments + Birthday!
The Cherno
3D Game Programming - Episode 17.5 - Creating an Applet
The Cherno
3D Game Programming - Episode 18 - The Beginning of Walls
The Cherno
3D Game Programming - Episode 18.1 - A Few More Things
The Cherno
Episode 18.5 - Creating an EXE File in Java
The Cherno
3D Game Programming - Episode 19 - Rendering Walls
The Cherno
3D Game Programming - Episode 20 - Continuing Walls, Fixing Bugs, and Managing Crashes
The Cherno
3D Game Programming - Episode 21 - Texturing Walls, Fixing Clipping, and Fixing the Mouse
The Cherno
3D Game Programming - Episode 22 - Random Level Generator + Properly Fixing Clipping
The Cherno
3D Game Programming - Episode 23 - Graphical User Interface (GUI) Launcher
The Cherno
3D Game Programming - Episode 24 - Making Our Launcher Work
The Cherno
3D Game Programming - Episode 25 - Writing and Reading Files
The Cherno
3D Game Programming - Episode 26 - Custom Resolutions
The Cherno
3D Game Programming - Episode 27 - Decorating the Launcher
The Cherno
3D Game Programming - Episode 28 - Continuing our Custom Launcher!
The Cherno
3D Game Programming - Episode 29 - Launching The Game
The Cherno
3D Game Programming - Episode 30 - Colour Processing In-Depth
The Cherno
3D Game Programming - Episode 31 - Sprites!
The Cherno
3D Game Programming - Episode 32 - Sprite Mapping
The Cherno
3D Game Programming - Episode 33 - High Resolution Rendering
The Cherno
3D Game Programming - Episode 34 - Entities
The Cherno
Genesis - My Game for Ludum Dare 24
The Cherno
Vlog + Ludum Dare Results
The Cherno
Game Programming - Episode 1 - Resolution
The Cherno
Game Programming - Episode 2 - Threads
The Cherno
Game Programming - Episode 3 - Game Loop
The Cherno
Game Programming - Episode 4 - Window
The Cherno
Episode 5 - Buffer Strategy
The Cherno
Game Programming - Episode 6 - Graphics Initialized
The Cherno
Game Programming - Episode 7 - Buffered Image and Rasters
The Cherno
Game Programming - Episode 8 - The Screen Class
The Cherno
Game Programming - Episode 9 - Rendering Pixels
The Cherno
Game Programming - Episode 10 - Clearing the Screen
The Cherno
Game Programming - Episode 11 - "Out of Bounds, Baby!"
The Cherno
Game Programming - Episode 12 - Negative Bounds
The Cherno
Game Programming - Episode 13 - Timer
The Cherno
Game Programming - Episode 14 - FPS Counter
The Cherno
Episode 15 - Tiles
The Cherno
Game Programming - Episode 16 - The Map
The Cherno
The Walls 2 - Minecraft PvP Survival Map
The Cherno
Game Programming - Episode 17 - Key Input
The Cherno
Game Programming - Episode 18 - Controlling The Map
The Cherno
More on: Systems Design Basics
View skill →Related Reads
📰
📰
📰
📰
O(N) Manacher's Algorithm with Mirror Boundary Optimization
Dev.to · Dipaditya Das
Building a Power Grid Inside Minecraft with BFS Algorithms
Dev.to · Carlos Cortez 🇵🇪 [AWS Hero]
The Run-Length Encoding Trick: How Simple Strings Get Compressed
Medium · Programming
75 Days of Leetcode — Day 4: #238 — Product of Array Except Self
Medium · AI
🎓
Tutor Explanation
DeepCamp AI