Rust and RAII Memory Management - Computerphile

Поділитися
Вставка
  • Опубліковано 4 лют 2025

КОМЕНТАРІ • 886

  • @cno9984
    @cno9984 Рік тому +767

    I like how neither his C++ or Rust code snippets would compile.

    • @badassopenpolling
      @badassopenpolling Рік тому +13

      correct hahaha

    • @KaneYork
      @KaneYork Рік тому +173

      The C++ has extra sneaky [Undefined Behavior] too, because he used `delete` instead of `delete[]`.

    • @MS-ib8xu
      @MS-ib8xu Рік тому +74

      I was wondering about that... I was thinking "surly they would have caught that, maybe it is a new feature in C++, the constructor can just be called Foo"

    • @leogama3422
      @leogama3422 Рік тому +80

      That's what 'pseudocode' means. It's for other fellow humans, not computers...

    • @klittlet
      @klittlet Рік тому +17

      Needless to say that is just for the purpose of explanation

  • @cowslaw
    @cowslaw Рік тому +707

    Rust’s borrow checker is one of the most powerful and strict features of any language I’ve ever used, and it’s absolutely wonderful!

    • @nicholas1460
      @nicholas1460 Рік тому +20

      Let's make a Groovy for Rust so we can ignore all that and turn it into an interpreter.

    • @alucard87
      @alucard87 Рік тому +7

      @@nicholas1460 absolutely! Lets bring gstrings everywhere!🎉

    • @nicholas1460
      @nicholas1460 Рік тому

      @@alucard87 The pervs have surfaced. Anyone has anything to do with the Groovy language is responsible for what they do.

    • @KX36
      @KX36 Рік тому +37

      meanwhile, every rust user: "unsafe { ... }"

    • @legotechnic27
      @legotechnic27 Рік тому +1

      There's stricter features in Dafny, but I'm not sure those are "absolutely wonderful". They certainly are very interesting though.

  • @refactorear
    @refactorear Рік тому +617

    9:19 I would say exactly the opposite, in this situation the best for your program is to crash, the worst is to get garbage and continue as if nothing had happened as it might takes months, years or decades to find out such a problem (especially when dealing with processing data and not knowing the kind of output you should expect). What usually happens, though, is that you get intermittent crashes depending on the memory values you get from that dangling pointer.
    Pretty sure the constructor and destructor in the C++ version needs to have the same name as the class, but that's besides the point of the video.

    • @Fs3i
      @Fs3i Рік тому +65

      I was gonna write that. The best case for a UAF is usually a crash, rather than silent data corruption, or revealing random memory. Both of them are security/safety risks, which can undermine everything your program does.

    • @bkucenski
      @bkucenski Рік тому +28

      Yep. When things break loudly, it's a big motivation to go fix it. You can also log exactly where the crash happened and the state to track what caused it so you can prevent the problem in the future.

    • @-dubu
      @-dubu Рік тому +23

      Fail early and loudly

    • @crateim
      @crateim Рік тому +24

      this! crashes are problems that actually got *detected* and *prevented* - crashes are your friends

    • @ClifBratcher
      @ClifBratcher Рік тому +13

      💯 The development time (money) involved in debugging the garbage cases is dramatically larger than failing fast.

  • @anafabula
    @anafabula Рік тому +371

    That "bob" variable you tried to use three times doesn't exist.
    And why not show the compiler output? It's very friendly

    • @chuxmyk
      @chuxmyk Рік тому +21

      Exactly. I was going to ask this. I kept searching for where it was defined since the argument passed was “b” and none in func_1.

    • @-dubu
      @-dubu Рік тому +54

      It’s not a rust tutorial, it’s explaining the idea of a borrow checker which it does fine

    • @jiayeelow
      @jiayeelow Рік тому +6

      Thanks for clarifying, I was thinking if somehow 'bob' and 'b' are the same variables...

    • @ze_rubenator
      @ze_rubenator Рік тому

      @@-dubu Still wary of learning anything from someone who doesn't appear to know what they're doing.

    • @a.modestproposal2038
      @a.modestproposal2038 Рік тому +103

      This kind of sloppiness does a real disservice to the channel and the intent of the video. You can't be bothered to COMPILE all your examples? Or at least "*" annotate the errors in the video? Such obvious errors are a disappointing distraction that pollutes the message.

  • @barbiefan3874
    @barbiefan3874 Рік тому +265

    09:20 - it's pretty much the other way around. Best case - your program crashes, worst - you get wrong data and use it.

    • @256shadesofgrey
      @256shadesofgrey Рік тому +18

      Depends on the program, where exactly in the program this problem appears, and how often it does so. For example if the value was storing the color information for a single pixel, and that value is garbage once every 10 million outputs, and all the program does is display images on the screen, I'd rather have that single pixel flicker with random colors once every 5 frames than have the program crash. At least as a user.

    • @YouPlague
      @YouPlague Рік тому

      @@256shadesofgrey This thinking is what leads to scanners giving you wrong numbers in your tax reports, look up "Xerox randomly changes numbers". The program should crash and make the developer fix it immediately, not try to ignore it forever.

    • @deadok0k
      @deadok0k 8 місяців тому

      @@256shadesofgrey Hehe, fun fact about Undefined Behavior - you just can't assume what would happen when it is triggered.
      As an example: you program might run on the same amazon cloud server as some Radionuclide therapy-software, and UB in your code might trigger some unknown exploit that breaks vm isolation and corrupts command list for RNT device.

  • @LuizDahoraavida
    @LuizDahoraavida Рік тому +284

    5:50 in C++ you need to tell the compiler if what you're deleting is an array with delete[] instead of delete. In that example the memory won't have been freed properly.

    • @LuizDahoraavida
      @LuizDahoraavida Рік тому +133

      I guess this just goes for show on how easily memory leaks can happen when the programmer is responsible for the memory management.

    • @kwanarchive
      @kwanarchive Рік тому +1

      @@LuizDahoraavida Just use std::vector.

    • @seth3129
      @seth3129 Рік тому +37

      @@LuizDahoraavida now you're getting it :) this is why rust was created in the first place: to eliminated a whole class of bugs caused by common and easy to make mistakes

    • @LuizDahoraavida
      @LuizDahoraavida Рік тому +7

      I just hope that wasn't on purpose

    • @kwanarchive
      @kwanarchive Рік тому

      @@seth3129 std::vector already existed from the beginning.

  • @Qazqi
    @Qazqi Рік тому +219

    It seems a little apples-to-oranges to have a raw pointer in C++, but have a vector in Rust. Both of the languages have a suitable vector type that uses low-level operations under the hood and packages that up into a nice-to-use type with the hard work done for you. Using the video's examples for the two languages makes it easy for people who aren't familiar with them to walk away with a very incorrect view of C++ that remains pervasive in the field, but doesn't reflect how ordinary code is written at all. The Rust comparison should come in at the point where it starts to offer more guarantees and functionality than what C++ can offer, and point out that it's part of the language rather than static analysis.
    Even moving (which C++ has too, just different) isn't so much about one owner for something like a vector (the vector already represents a single owner of its memory) as it is about not needlessly copying the vector. Either way works, but one makes copies explicit. There are other contexts where it's more about a single owner for a resource. Borrow checking and trying to use something after it's been moved from are where Rust really starts to bring more to the table in this regard than static analysis with accompanying rules on how to write code so the analyzer can reasonably work with it.

    • @claytorpedo
      @claytorpedo Рік тому +46

      This is the same problem I have with most Rust vs C++ comparisons -- you get someone who appears to have virtually no knowledge of C++ that isn't at least two if not three decades out of date confidently saying why their insanely contrived example that no real person would ever do could be better in Rust. I strongly suspect there are things that _would_ be nicer for me in Rust, but instead I just keep seeing crappy Rust salespeople that don't know any C++ but try to pretend that they do.
      This person doesn't even seem to know how the very basic fundamentals like how constructors and new/delete works (this feels too extreme to be live-demonstration nerves, and insane they didn't doctor it in post), so I'm very doubtful they ever knew anything about C++ at all.
      From what I understand, most of what Rust brings to the table is advanced static analysis, which is great, but C++ has a decent amount of that too (e.g. use-after-move or use-after-free).

    • @TheJaguar1983
      @TheJaguar1983 Рік тому +20

      Yeah, happens a lot. I find a lot of Rust programmers are super into it, espousing all of it's pros, why everyone should use it and usually comparing it to C++. There's also an element of functional vs object-oriented where they all espouse functional or functional-style programming to be *always* superior to OOP despite the fact that OOP is still one of the most common programming paradigms in the world. They all seem to be drinking for the same fountain that says "this is why Rust is better than C++", but don't actually know anything about C++ beyond the base language and usually the 98 standard.
      Rust is kind of a cult and those who love it think every other language is terrible, especially C++.
      Personally, I love Python and C++, but I'll use whatever suits the task best.

    • @bruhe_moment
      @bruhe_moment Рік тому +38

      ​@@claytorpedothe advantage of rust isn't that it *offers* static analysis, it's that it *forces* static analysis by default.
      Someone who knows very little C++ is very likely to make this sort of mistake without knowing how it could've been prevented.
      Someone who knows very little Rust won't make this mistake because the compiler defaults don't allow for it.

    • @trapfethen
      @trapfethen Рік тому +52

      The video is not demonstrating the Best Practices of both languages and how THEY differ. It is demonstrating the MINIMUMS of the language and how they differ. You can constrain C++ to get much of the same benefits as rust, with the added boilerplate, static analysis configurations, and code-style enforcement that comes with that. Even with all those things, it is still POSSIBLE to create these kinds of bugs because the language allows these unsafe operations BY DEFAULT and won't warn or flag that you are doing something that may cause issues. In rust, if you wish to do these types of operations for the few valid use-cases where they are unavoidable, you HAVE to tag that block as unsafe. In the event of a crash, that is going to be the FIRST place you look.

    • @TheJaguar1983
      @TheJaguar1983 Рік тому +5

      @@trapfethen Thank you for providing a balanced analysis.

  • @GingerGames
    @GingerGames Рік тому +69

    This video conflates RAII and ownership semantics quite a bit. This is a common misconception but if this is meant to be an introduction to either concept, this will most definitely confuse a newcomer to these concepts. You can explain Ownership Semantics without ever referring to RAII whatsoever and vice versa. Ownership semantics can be used to aid with a few issues that RAII in C++ causes (such as over use of copy constructors) but they solve different orthogonal problems entirely.
    C++11 onwards also has all of these ownership semantics (rvalue references, std::move, std::forward, etc), but they are an opt-in thing rather than something that is required like in Rust.
    Also, if you are wanting to reduce resource usage as much as possible, RAII is not the right tool for you and will most likely cause you to waste more memory than other approaches.

    • @kwanarchive
      @kwanarchive Рік тому +7

      How does RAII cause you to waste more memory?

    • @zsomborhollay930
      @zsomborhollay930 Рік тому +8

      RAII don't waste any resource, it's just a method to handle object states.

    • @noahhounshel104
      @noahhounshel104 Рік тому +2

      I'm not sure I agree at all. This video isn't confusing RAII and ownership semantics at all, but is illustrating how RAII must be handled and enforced for it to work properly. To allow RAII to work at all, the borrow checker/ownership semantics have to be enforced.
      How is this conflating RAII and ownership semantics?
      I'm also unsure how RAII is "wasting memory" to be honest. Rust automatically drops things that go out of scope, but you can also drop things at any point.

    • @GingerGames
      @GingerGames Рік тому +5

      @@noahhounshel104 ​ @kwanarchive ​ @Zsombor Hollay
      RAII on its own does not necessarily waste memory compared to other approaches, however the general culture assumes RAII means you should allocate singular things instead of thinking about your allocation separately from your single objects. As a result, a lot of memory is wasted because you off-load the allocation aspect to the single object, whereas RAII could still be useful if you did not do this.
      Another issue with C++ specifically is that they conflate construction/destruction with allocation/deallocation. It is extremely useful to want to allocate an object and then construct it at a later time, destruct it and then deallocate it at a later date, but due to the way C++ has been designed and the culture around C++, most people couple them together (making things bad). Constructors and destructors also do not "return a value" meaning that the only way you can signal something may have gone wrong is by throwing an exception (which might be a huge issue depending on the problem space). This is why many people will just use explicit `init` and `destroy` functions/methods instead of relying on the ctors/dtors, thus bypassing many of the features of RAII.
      I can give you loads of real world examples of codebases that use RAII heavily that are extremely wasteful of memory (compared to other approaches). And to clarify, RAII is not inherently wasteful but the culture around it and how it the languages that have tend to be designed nudge you to use it in such a way that is extremely uncaring about memory allocations by making them hidden.

    • @noahhounshel104
      @noahhounshel104 Рік тому +2

      ​@@GingerGames Eeehhhh. I suppose you can view RAII as "wasteful" if you are never deferring the creation of the objects to a later date, but in the Rust world doing so would just be an Option which is useful/important for a whole host of reasons besides having deferred allocation.

  • @deconline1320
    @deconline1320 Рік тому +215

    Even though the goal here was to demonstrate Rust RAII mechanism, it's worth mentioning that modern C++ provides equivalent concepts using unique_ptr and moves. Nowadays, you rarely need to delete memory manually in C++.

    • @bertiesmith3021
      @bertiesmith3021 Рік тому +63

      You can still get dangling references pretty easily. Rust solves this with lifetime analysis. This can often be picked up in c++ through static analysis but Rust guarantees that dangling references won’t compile. The c++ is very poorly constructed - just accessing the data() function of std::vector would have been a better example to construct a dangling reference.

    • @TheJaguar1983
      @TheJaguar1983 Рік тому +52

      It's the usual Cult of Rust propaganda: Rust is the best, everything else is bad, especially C++

    • @slyfox3333
      @slyfox3333 Рік тому +1

      @@TheJaguar1983 C++ Stockholm syndrome in action

    • @TheJaguar1983
      @TheJaguar1983 Рік тому +15

      @@slyfox3333 Typical one-eyed Rust fanaticism.

    • @slyfox3333
      @slyfox3333 Рік тому +61

      @@TheJaguar1983 cope

  • @br3adina7or
    @br3adina7or Рік тому +259

    The reason you can't borrow mutably and immutably at the same time isn't because one function is expecting the data to be unchanging while another is expecting it to be mutable. If that was the case, as you are presenting, multiple mutable references would be allowed at the same time, when they very much aren't. Mutable references are meant to be exclusive so there's only ever one point of mutation for a given piece of data (and no immutable references at the same time), which is done in order to avoid data races and the such. This is why mutable references are often called exclusive references and immutable references are often called shared references. This principle is also applicable to `Rc`, which was mentioned. Rc basically gives shared references to the data, but it cannot be mutable; to have shared mutable data, one would have to use one of the interior mutability data structures (in the case of an `Rc`, you'd probably want a `RefCell`).
    I think it's important to make this clear when introducing the topic of references in Rust, because one of the core design principles is "fearless concurrency", and as such that is baked into its fundamental ownership principles. That is to say, these concepts are inherently tied in Rust. I don't know if this was an intentional simplification, but it's something that shouldn't've been omitted imo.
    As an aside, `Rc` and `Arc` aren't really like garbage collection. Like, they can be used like garbage collection, but basically instead of having a garbage collector go through the memory and seeing what should be dropped, `Rc` and `Arc` keep an internal counter and then increment it when cloned and decrement it when dropped. When an `Rc`/`Arc` is dropped and there's no more references, it just drops the underlying data. This means that using these smart pointers has a slightly different cost to the equivalent code in a garbage collected language. (Though this isn't really a major point.)

    • @valcron-1000
      @valcron-1000 Рік тому +22

      GC is not just mark and sweep. Reference counting is a form of garbage collection

    • @pcfreak1992
      @pcfreak1992 Рік тому

      I was going to post the same comment but you worded it better than I could have 😅

    • @mokuzzai8906
      @mokuzzai8906 Рік тому +12

      also having multiple mutable references might cause data to become invalid. imagine taking a eference to the first item in a vector, and then overtiting the vector with an empty one. now our reference points to unitialized memory

    • @trisinogy
      @trisinogy Рік тому +4

      Basically you pretended to "fix" something the video doesn't say in the first place, and failed to do so. I am used to this pointless pedantry on StackOverflow: not ready to face it here on YT, frankly.

    • @peter9477
      @peter9477 Рік тому +10

      @@valcron-1000 I think the term GC is often misused that way, but I don't think it's correct. Python, for example, has a garbage collector, but it also has ref counts, and the GC is only there to clean up things the ref counting can't handle fully (like cycles). You can't have garbage collection without a garbage collector, and Rust definitely doesn't have one (any more).

  • @tropicbliss1198
    @tropicbliss1198 Рік тому +79

    It’s worth noting that rust has type inference, so you don’t have to specify your type every declaration of a variable

    • @johnyepthomi892
      @johnyepthomi892 Рік тому +2

      @MenaceInc Well it would be a shame if it doesn’t 😂

    • @NuclearCraftMod
      @NuclearCraftMod Рік тому +28

      @MenaceInc While you’re correct, C++‘s type inference, which is similar to Java’s, C#’s, etc. isn’t _quite_ as powerful as Rust’s, which is more like those found in functional-first languages. For example, in C++, you can’t write something like “auto x;”, while “let x;” is valid in Rust (provided the type of x actually can be uniquely inferred by how it’s used).

    • @konga8165
      @konga8165 Рік тому +6

      If you have rust-analyzer installed you also get phantom type hints inline with your code which makes it so nice to read. No need to hover over variables to see the type like other languages. This seems small but it's so nice.

    • @jakubrogacz6829
      @jakubrogacz6829 Рік тому

      @@NuclearCraftMod That is not a problem of language but of compiler standards.

    • @HoloTheDrunk
      @HoloTheDrunk Рік тому

      @@konga8165 Many of the popular languages's LSPs have that kind of functionality though..? It's just returning more information to the editor following the LSP standard.

  • @mo_i_nas
    @mo_i_nas 10 днів тому

    Honestly. I've tried to learn this stuff so many times and I basically gave up. This computerphile video was exactly what I needed. Thank you very much for this

  • @konga8165
    @konga8165 Рік тому +38

    Huge fan of Rust. I've been writing it in production for over a year now and it's been a dream to work with.

    • @gr.4380
      @gr.4380 3 дні тому

      I could only dream...

  • @myronkipa2530
    @myronkipa2530 Рік тому +50

    Some of the things Rust does the right way:
    1. RAII or memory ownership model - follow few rules and forget about memory leaks
    2. Traits composition instead of trait inheritance.
    3. Powerful enums/unions - can hold values. You have to consider all cases
    4. Pattern matching
    5. No NULL. Instead - enum with optional value
    6. Powerful macros
    My main complaint with rust is that compiler won't let me be silly and write bad code. This also means it won't let you shoot yourself in the foot. But the learning curve is a bit steep. Rust is so different from other languages

    • @ifcoltransg2
      @ifcoltransg2 Рік тому +10

      Rust is inconvenient to prototype things in. That's probably why we see a lot of Rust rewrites of existing programs, that already got prototyped decades ago.

    • @0x5DA
      @0x5DA Рік тому +9

      @@ifcoltransg2 for some stuff. though, i actually find myself specifically leaning to rust to prototype in, because the way one lays state out makes it a lot easier to understand how the program would work, for me

    • @ifcoltransg2
      @ifcoltransg2 Рік тому +7

      @@0x5DA I did overgeneralise. I guess Rust's type system is great when you want to make sure things end up correct and well structured. It gives you some support there to create a solid foundation. But I do find, for the kind of project you just want to get working, it's easiest to throw up some Python onto the screen first, rewrite it in a type system after.

    • @0x5DA
      @0x5DA Рік тому

      @@ifcoltransg2 i get that, for making it work! no worries

    • @HoloTheDrunk
      @HoloTheDrunk Рік тому +4

      ​@@ifcoltransg2 After using rust for personal projects and then nearly a year in production, I now find it much easier to prototype complex ideas in.
      The biggest help it provides is in easily helping you design your data model in a way that your program can never reach an invalid state (mostly thanks to the absence of null or similar and the conciseness of enum variants).
      Nowadays when prototyping something I usually go to Rust first because I know that if there's a lib to do what I want it'll 9 times out of 10 (if not more) have standardized, easy to navigate documentation and the auto-completions brought about by the strict type system will guide me through the process.
      I do agree with the OP on that it takes quite a bit of time to learn and even more to become actually proficient in it (not even mastering it, just being able to "realistically" pick Rust for a time-sensitive project); I wouldn't ever recommend it to someone as a first programming language.

  • @oussamawahbi4976
    @oussamawahbi4976 Рік тому +1

    rust newbie here, this is possibly the best introductory explanation to the rust borrow checker i saw on the internet

  • @kadlubom
    @kadlubom Рік тому +91

    Shouldn't the constructor be 'Bob' not 'Foo' though?

    • @Faladrin
      @Faladrin Рік тому +9

      I've not coded in C/C++ for a long time and I was having an aneurism when I saw that and wasn't sure if the code was wrong or my memory. Thanks for the comment letting me know I was right!

    • @Am6-9
      @Am6-9 Рік тому +5

      I think its the other way round, the Class should be called Foo, not Bob…😊

    • @alcoholrelated4529
      @alcoholrelated4529 Рік тому +10

      @@Am6-9 yeah, Bob should be called Robert

  • @catwhisperer911
    @catwhisperer911 2 місяці тому

    I'm an old C/C++ programmer and this was an excellent overview of Rust memory management. Thank you.

  • @TJ-hs1qm
    @TJ-hs1qm 10 місяців тому +1

    The explanation was perfectly fine for me, on point. There are millions of other channels to learn about the syntax 👍

  • @mihir2012
    @mihir2012 Рік тому +109

    I think this was explained quite poorly. You can write as much garbage code in any language you want, including rust. What matters is that when you try to compile the code, the rust compiler rejects much more (memory related) garbage than the c/c++ compiler does. Whereas c/c++ will allow you to get to runtime and may or may not crash then, rust doesn't allow you to get to runtime at all until you have fixed these issues. And not once you showed any compiler output at all. Which is also probably why you kept using variables that don't exist at all.

    • @sobanya_228
      @sobanya_228 Рік тому +8

      Rust is like switching to a properly strictly typed language after coding in some poorly typed codebase in a gradually typed language.

  • @JR-mk6ow
    @JR-mk6ow Рік тому +12

    I work as frontend and I've started using Rust because I was missing messing around a low-level language. I'm in love! It's harder than JS (and way slower to build anything) but the borrow checker and the compiler are so so so good.

    • @pyyrr
      @pyyrr 10 місяців тому

      just use c++ rather than an esoteric language like rust

  • @philosophyze
    @philosophyze Рік тому +35

    I've been learning Rust this last year. Love it.

  • @FPSMinecraftable
    @FPSMinecraftable Рік тому +129

    Shouldn't constructors in C++ have the same name as the class?

    • @Hexalyse
      @Hexalyse Рік тому +77

      If this was the only error in this video. Most variable and parameters names were wrong in the Rust example (n becoming bob, b, becoming bob, etc.). I liked the video but it was a mess. Trying to compile the code to show what it does would have allowed to detect those problems.

    • @AlFredo-sx2yy
      @AlFredo-sx2yy Рік тому +37

      @@Hexalyse also delete instead of delete[], among other things, filling this video with tons upon tons worth of UB.

    • @Finkelfunk
      @Finkelfunk Рік тому +14

      @@Hexalyse That is the issue with academic CS though. They are more interested in concepts and less in being code monkeys. They can design the most complex ideas and constructions, but in the end the people that work with the language on a daily basis will know a language better than they do.

    • @NeatNit
      @NeatNit Рік тому +14

      @@Hexalyse It seems to me like all, or nearly all of these errors would have been caught if he just tried to compile his code after each demonstration. And actually *demonstrate.*
      But to be fair, he seemed a bit nervous in front of the camera and I don't blame him for getting lost. Next video will be better, I'm sure of it :)

    • @jongeduard
      @jongeduard Рік тому +3

      @@Hexalyse Explaining and coding at the same time is not the best option for everyone I guess! 😆😁
      Probably it would have been a better idea to first write and test all code first before showing it in a presentation.
      Explanation was fine though.

  • @h-0058
    @h-0058 Рік тому +45

    Nice video, the Rust borrow checker is pretty cool, but the C++ comparison didn't make much sense. C++ has had smart pointers for 12 years now (maybe more with boost), which get rid of all the problems except dangling references. You never write new and delete in C++, you never use raw pointers that own memory, you can move or only "borrow". The only thing where standard C++ will not help you is if you borrow a pointer and try to access it after the owning pointer deleted the memory (so dangling references).

    • @hanifarroisimukhlis5989
      @hanifarroisimukhlis5989 Рік тому +4

      Smart pointer still sucks though. Not everyone will use it, and adds complexity. Atleast Rust understands what you're doing and prevent errors before you spend hours debugging.

    •  Рік тому +1

      There are a few more things C++ won't help you with but yeah, this was kinda strawman argument.

    • @valizeth4073
      @valizeth4073 Рік тому +6

      C++ has had RAII capabilities since the 80's even, it was just made more nicely with the addition of move semantics.

    • @toby9999
      @toby9999 Рік тому

      I still use new and delete and never have a problem with it.

    • @TheJaguar1983
      @TheJaguar1983 Рік тому +7

      @@hanifarroisimukhlis5989 Not true. Smart pointers are excellent. On the other hand, the time you save on debugging with Rust, you waste fighting the borrow checker.

  • @fllthdcrb
    @fllthdcrb Рік тому +17

    21:01 You also can't have a mutable reference to an immutable variable, which Ian had at this point. And regarding mutable and immutable references, it's not just that you can't have both of those, you can't have _any_ other references, mutable or immutable, if one of them is mutable, for similar reasons. (It's a little more subtle, though. For these purposes, Rust only cares about the span of execution when the variable is actually used. That's why the example with moving an object from one variable to another is fine, because after that the first variable isn't used. In the same way, you can declare and use multiple mutable references to the same object in the same scope, as long as the regions where they're used don't overlap.)

  • @germandkdev
    @germandkdev Рік тому +82

    Thank you for this explanation of RAII, it was really interesting. But nearly all examples shown wouldn't run as either variables or methods are wrongly named. (Foo constructor in Bob, bob instead of b in all rust functions)

  • @Speglritz
    @Speglritz Рік тому +49

    Great video. One remark would be to try compiling your examples next time. I think people unused to these languages could become confused when the code isn't accurate.

  • @spark_coder
    @spark_coder Рік тому +3

    This is a very thorough explanation... thank you for that...
    But I must point out that at 5:45 inside the cpp program, within the destructor, the use of the delete keyword (delete this->n) in order to deallocate the array is wrong since it only removes the first element as the array is technically a pointer, therefore you would have to use the delete[] keyword (delete[] this->n) or loop through and delete each element.
    Thank you for this wonderful video ❤

  • @irlshrek
    @irlshrek Рік тому +9

    awesome video! there are so many interesting things in rust! hopefully we get more Rust content

  • @Firepipproductions
    @Firepipproductions Рік тому +8

    6:32. RAII doesn't put allocation/deallocation as work on the programmer. The programmer can use STL containers and pretty much never use the keyword new. It is called rule of 0 and is the core essence of modern C++.

  • @FalcoGer
    @FalcoGer Рік тому +35

    Your constructor and destructor for class Bob should be Bob and ~Bob, and not Foo and ~Foo.
    If you allocate an array with new, you need to use delete[] to clean that up, not just delete.
    In your rust code, you refer to bob when you variables are named n and b. Maybe you should get an IDE that highlights errors for you. Vim is great and all, just use syntastic or some other plugin to do that for you.
    Bare pointers are fine so long as it's simple and easy and there is no chance of accessing memory after it has been freed or it being very unlikely that you forget something. You should just use smart pointers instead otherwise. Unfortunately something that starts out simple can quickly grow in complexity and if you are not careful designing your API to your bob instances, someone might pull a pointer and use it outside some scope. Instead of trying to remember to allocate and clean up in two different spaces, you should just let the smart pointers handle that for you. They are well optimized. They do of course have their own drawbacks like cyclic dependencies that need to be watched out for, but generally they are the better choice.
    In your Bob example, a unique pointer would simply not work as you can't copy it without handing over ownership, and a shared pointer would work just fine, although you still wouldn't want to just return it like that as n probably makes no sense without bob. A weak pointer is probably the right choice here.
    If you want a fair comparison, then bob in c++ would also hold onto a high level structure, like std::vector, instead of a bare int[].

    • @oracleoftroy
      @oracleoftroy Рік тому +5

      Err, no, an array of int would be represented by int*.
      int *x = new int; // fine
      int *y = new int[5]; // also fine
      delete x; // correct delete for single item
      delete [] y; // correct delete for array
      int ** would be an array of array of ints or a way to pass an array by reference in a C-style function so that you could (re)allocate it.
      But you are right about the rest, std::vector is almost always preferred if you need a dynamic array, or std::array if you don't.

    • @FalcoGer
      @FalcoGer Рік тому +1

      @@oracleoftroy fixed it. you are correct.

  • @Devills_hill
    @Devills_hill Рік тому

    Am i the only one watching this, finding it super interesting every single upload yet understanding about 5% of what they tell u?

  • @ToadalChaos
    @ToadalChaos Рік тому +2

    So long as a mistake can be made, it will be made eventually.
    To me that's one of the greatest strengths of Rust. It prevents you from making common mistakes by being opinionated enough in it's design.

  • @wiserdivisor
    @wiserdivisor Рік тому +4

    This guy knows neither C++ nor Rust.

  • @shahinza
    @shahinza Рік тому

    Thank you for sharing this excellent video! I truly appreciate the effort put in by education professionals like you to create such valuable content.

  • @Amejonah
    @Amejonah Рік тому +5

    2:37 This is NOT the same as in other languages. Val in Kotlin, final in Java, etc. makes the variable itself not reassignable not immutable.
    final var person = Person(19);
    person.setAge(20);
    does mutate the variable even if it has final. In Rust, however, you cannot* mutate the variable at all (as for age_set(u16) you would need a mutable reference).
    (* ignoring concepts like internal mutability using RefCell (assures the 1 mut xor n imut rule at runtime instead of compile time), unsafe and such)

  • @timokreuzer1820
    @timokreuzer1820 Рік тому +18

    So Bob has a constructor called Foo? And the scalar delete operator is used in the destructor to delete the array allocated with operatot new[]? And b gets automagically renamed to bob in Rust? I guess we are dealing with a computer scientist here.

    • @TheJaguar1983
      @TheJaguar1983 Рік тому +1

      Nah, just your average Rust evangelist.😝

  •  Рік тому +1

    Cool that you made a video about Rust!

  • @gosnooky
    @gosnooky Рік тому +4

    Immutability works much differently in Rust than in TS. In TS, when dealing with non-scalar values such as objects or arrays, a const won't allow the value itself to change (e.g. memory address), but you can still push to an array or add a property to an object. In Rust, it's an effective Object.freeze by default where you still need to declare "mut" to allow modifications to the underlying compound value. This is a very important distinction.

    • @heto795
      @heto795 Рік тому

      Lack of mut in Rust is much closer to const in another language... C++. When applied directly to an object (like a variable), the meaning is basically the same in both languages (but there is a significant difference when applied to the type of a reference). Whether for the presenter's lack of C++ expertise or another reason, this video makes it look like the difference between C++ and Rust is many times greater than it actually is.

  • @zamf
    @zamf Рік тому +14

    What wasn't mentioned is that the C++'s standard library is build around RAII and the notion of moving data around, so the concept is not new for Rust. Rust just enforces it by the compiler, while C++ lets you use RAII as well as unsafe resource management.

    • @TheJaguar1983
      @TheJaguar1983 Рік тому +9

      Rust programmers tend to not know that because they're too busy running down other languages' flaws

  • @martinparidon9056
    @martinparidon9056 17 днів тому

    Exactly the video I needed, thank you!

  • @СергейМалышев-м9р

    You absolutely wrong when tell about C++. C++ already has RAII classes in STL, and in most cases you do no need to handcraft memory management.
    Also, resources are not only the memory, as other commentators mentioned, it might be any thing what you get from OS, like: window handles etc.
    The key difference in C++ and Rust is move by default in rust, and borrowing.

  • @bazoo513
    @bazoo513 Рік тому +7

    ˇ2:45 : Well, C and Java also have construct to declare something to be a constant. All Rust does is make "constantness" the default, and one has to specify mutability ("variability") using an additional keyword.
    It's not like other languages are like Fortran V on Univac 1100 series under EXEC8, where even integer literals were actually mutable variables passed to subroutines by reference. Now, _that_ was a source of some really nice puzzles for novices.

  • @vadumsenkiv8773
    @vadumsenkiv8773 Рік тому +6

    So, in the C++ sample you use raw pointers and manual memory management, which is not recommend in modern C++, and you could use std::vector and return it by copy, move or const reference then you'll get the same behavior as in Rust or whatever you can want 🤷
    And don't forget about references in C++ too.
    However, I agree that more control that C++ gives to developer requires a lot more responsibility.

  • @cthree87
    @cthree87 Рік тому +1

    Nice to see y'all covering Rust

  • @Raspredval1337
    @Raspredval1337 Рік тому +21

    6:30 no, you don't have to write that urself, that's where stl comes in: we have generic containers, like std::vector for storing generic data, std::string is a text container and std::unique_ptr\std::shared_ptr are RAII wrappers, that do basically the exact thing you've shown: it would allocate an object for you, keep track of the memory and delete it, when the object(or all of the objects, that point to the resource) goes out of scope.

    • @AlFredo-sx2yy
      @AlFredo-sx2yy Рік тому +2

      he's also doing it wrong. He's meant to delete[] because he allocated a sector of memory, not a single element. In most unix systems and linux distros that is not a problem because the allocator used works just fine either way, as it simply writes how much memory has been stored using a size_t chunk of memory just before the first element. But in the case of windows for example, that is not the case, the allocators are different, and many other systems could be using a different allocator, so using a delete there is UB. More evidence that we should not blindly trust all the things we're told by people on the internet.

  • @candysugar5681
    @candysugar5681 Рік тому +47

    Why do you intentionally write bad code in C++ to elevate Rust? I'm sure the Rust community doesn't want you doing that.

    • @vectoralphaSec
      @vectoralphaSec Рік тому +1

      Right. C++ solves this problem with std::unique_ptr.

    • @kwanarchive
      @kwanarchive Рік тому +11

      The code is bad, but it's also more code than necessary. He had to go out of his way to make an issue, whereas one std::vector would have solved the problem.

    • @micahrufsvold
      @micahrufsvold Рік тому +9

      I think you're forgetting the audience this video is for. A lot of people watching this don't know about rust, c++, or memory management, and they aren't going to be coding embedded code any time soon. He just needed to demonstrate clearly and quickly the memory management problems that Rust's ownership model is trying to solve. This isn't a sales pitch for programmers, it's educational content for laypeople.

    • @CamaradaArdi
      @CamaradaArdi Рік тому +3

      It's really easy for a new programmer that doesn't know about smart pointers to fall for those traps. If he wanted to make that point he probably should had used C.
      Rust is better than C++ for other reasons so you're right, no need to write bad C++

    • @shadamethyst1258
      @shadamethyst1258 Рік тому +3

      The point is also that you *can* write memory unsafe C++, despite following rules like RAII, whereas you can't in Rust, unless if you write "unsafe" somewhere.
      He could've presented an automatic code analysis tool for C++ that implements the move/borrow semantics and gotten to the same result, but rust has that tool built in and a syntax that is built around the move/borrow semantic, so why not use that instead.

  • @adamd0ggg2
    @adamd0ggg2 Рік тому +9

    After learning Rust, my best advice is to write it without using borrows at first. Do a lot of copying and returning new objects. It is not efficient but it trained my brain to think about the memory allocation and moving process. Then borrows felt like a natural optimization.

  • @taufiqulalam2035
    @taufiqulalam2035 Рік тому +3

    The C++ code is wrong in the video. First off, the constructor name. And also, in C++ if you allocate an array you gotta use delete []. The concepts were explained somewhat vaguely. I recommend anyone trying to learn this, trying to the same stuff you do in C++ just write in Rust, and the compiler will automatically guide you towards the right way to do things. In C++, it will just let you do that stuff, no problem.

  • @Matt23488
    @Matt23488 Рік тому +2

    Yay a video on Rust!

  • @Ceelvain
    @Ceelvain Рік тому +14

    RAII must be one of the biggest misnomer in programming. The core of the concept is not to bind resource acquisition to the initialisation of a variable. But rather to bind the resource release with the destruction of a variable.

    • @gehngis
      @gehngis Рік тому +2

      The core concept is to bind the resource lifetime to a variable lifetime. This includes both binding the resource acquisition to the initialization of a variable and binding the resource release to the destruction of a variable.
      That's why languages without constructors like Rust cannot fully implement RAII as they cannot bind the resource acquisition to the initialization of a variable.
      The resource has to be acquired and then binded to its RAII variable, if stack unwinding happens between the resource acquisition and its binding, the resource won't be released.

    • @hanifarroisimukhlis5989
      @hanifarroisimukhlis5989 Рік тому

      ​@@gehngisnot really, when the stack unwounds the resource is dropped/released, unless releasing such cause further exceptions.

    • @gehngis
      @gehngis Рік тому

      @@hanifarroisimukhlis5989 no stack unwinding does not cause resources to be released. It just destructs variables. If a resource isn't held by a RAII variable it won't get magically released.
      Releasing resources can mean anything like making a system call, sending USB data to a device or sending a network packet to a server. Rust, or any language, cannot do that on its own that why we have RAII: to make the system call/send USB data/send network packet in the destructor of a variable which holds the resource.

    • @Ceelvain
      @Ceelvain Рік тому +1

      @@hanifarroisimukhlis5989 I think he meant if an exception occurs between (for instance) a malloc and setting the field RAII-variable. Then we would get a memory leak.
      Which is true, but it would be true of any RAII system. The resource allocation and the binding cannot be made in one atomic step.
      And my point was exactly this. We dont actually really care about the specific details of the steps to acquire a resource. What we care about is that the bulk of the code cannot leave a resource unreleased.
      Also, it doesn't actually matter if the variable initialisation happened miles before the resource is bound to the variable. As long as it is bound ASAP after it's been acquired in order to avoid the case mentioned above.
      Hence, it'd be better called DIRR. Destruction Is Resource Release. Or RRID.
      You know what? Let's try to popularise those names. 😆

    • @digama0
      @digama0 Рік тому

      ​@@Ceelvain In rust it definitely doesn't matter whether the value is bound or not to whether there is a gap in which a panic (aka exception) can cause a memory leak. There is no gap, when these things are lowered to the low level intermediate language all temporaries have bindings and drop elaboration happens at this level. All possible code paths are covered, including the panicking ones.

  • @raulwolters2380
    @raulwolters2380 Рік тому +3

    The "many read-only or one read/write reference" rule is also part of the dangling pointer protection. Imagine you have a Vector with a bunch of elements, and you take a reference to one of those elements. Suppose you were to now extend the vector. In that case, you might exceed the allocated capacity, causing the whole thing to be moved to another place in memory -> your reference to the original vec (which has now been deallocated) is now invalid. Besides that, not allowing two mutable references also prevents data races, which are considered unsound in rust.
    It might also be worth mentioning that memory leaks are not considered unsafe or unsound in rust and are totally possible with safe rust(Box::leak, or having reference counted smart pointers point to each other in a loop like Rc1 -> Rc2 -> Rc1).

    • @JasonHise64
      @JasonHise64 Рік тому +2

      The vector case you mention is critical. I’ve had bugs in a C++ program just due to passing a reference to an element on the stack along with a reference to the object containing the vector. Way farther up the callstack that vector grew and the reference on the stack got silently invalidated.
      Because of how complex the code had grown, going back and refactoring to eliminate this ‘unsafe borrowing’ was completely impractical, and the easiest way to fix the bug was just to create and use a new ‘paged’ container instead of a vector to ensure that growing the container would never invalidate references.
      If it had been written in rust from the get-go, that code would have failed to compile early on, long before so many dependencies were written on top of it!

  • @danielmilyutin9914
    @danielmilyutin9914 Рік тому +4

    5:40 you meant 'delete[] this->n;'
    in C++ there is difference between 'delete' and 'delete[]'.

  • @pierreabbat6157
    @pierreabbat6157 Рік тому +3

    C++ nitpick: you can't have a function ~Foo in a class named Bob. The destructor has to be named ~Bob, and similarly for the constructor.

  • @badassopenpolling
    @badassopenpolling Рік тому +1

    Class name is Bob and constructor/destructor name is Foo.
    This is something new added to C++ by Ian !!!

  • @cyndicorinne
    @cyndicorinne Рік тому

    I like how by 4 minutes in I already picked up something interesting from this.

  • @Gorzoid
    @Gorzoid Рік тому +2

    6:00 this is Undefined Behavior btw, you are not allowed to call delete on a pointer allocated using new[]
    Correct way to free it would be delete[] this->n;

  • @Omnifarious0
    @Omnifarious0 Рік тому +7

    6:21 - You have an error. You didn't use the right form of delete. You need to delete arrays differently. In this case, it probably will be just fine.
    Also, you keep saying "C" and then using "C++". They're different languages.
    Lastly, the appropriate comparison is not to bare C++ pointers. I hardly ever use those anymore in writing C++ code. The proper comparison is C++'s unique_ptr and shared_ptr. The concept of mutable and non-mutable borrowing doesn't exactly exist with those. But those are the closest equivalent to what Rust is doing.

  • @alibarznji2000
    @alibarznji2000 Рік тому +1

    What I've realized by studying different programming languages for around 5 years is that the harder the language, the better "programmer" it makes you in the long run, I think a lot of people can code using a language like python or JavaScript, but very few could even begin to understand the many rules and regulations of low level languages.
    Unless you're absolutely stubborn about learning a low level language, you won't be able to cope with it

  • @elwood.downey
    @elwood.downey Рік тому +2

    Finally! A clear and succinct description of what rust is about.

  • @razt3757
    @razt3757 Рік тому +3

    You should also take a look at Zig.

  • @IamAbdulQadeerKhan
    @IamAbdulQadeerKhan Рік тому +4

    Can you please share the NeoVIM configuration used by Ian in the video?

  • @remrevo3944
    @remrevo3944 Рік тому +1

    10:40 Semantically Vec isn't really the same as the example in C++. Box would be more fitting.

  • @roryboyes2307
    @roryboyes2307 Рік тому +4

    I don't know any rust. Isnt the ownership principle the equivalent of using std::move on a unique pointer in c++ only here it's the default pointer behavior?

    • @laundmo
      @laundmo Рік тому

      ownership in rust is quite tightly linked with lifetimes, which (as far as i know?) c++ has no equivalent t

    • @AbelShields
      @AbelShields Рік тому +1

      Rust moves are destructive moves, whereas C++ has to leave the moved-from object in a valid state even if it's not used again.

    • @CryZe92
      @CryZe92 Рік тому

      The differences are: Moves are the default, deep copies (called clones) are the explicit alternative. Also moves are "destructive" where the compiler doesn't let you access the variable anymore. In C++ moves put the object into a "valid but unspecified" state, which is a little bit odd for types that don't necessarily have such a concept. Like what's a valid but moved mutex, thread, file, tcp stream, etc? For a lot of types there's an equivalent of a null value, but for those that I mentioned the classes need to do some special "bool is_moved" or so and probably throw an exception on all the methods? It's really weird.

    • @BohonChina
      @BohonChina Рік тому +2

      C++ unique_ptr and shared_ptr are just like Box Arc in Rust.

  • @31redorange08
    @31redorange08 Рік тому +1

    9:17 Isn't it the other way around? The crash being the best case because continuing with garbage is very dangerous?

  • @NataNeverrain
    @NataNeverrain Рік тому +3

    5:50 Shouldn't it be
    delete[] this->n;
    missing the array.

  • @awwastor
    @awwastor Рік тому +2

    Rust doesn’t actually prevent memory leaks. It is fully possible to leak memory in safe rust, although a little harder. This is demonstrated by std::mem::forget, which was at one point unsafe, but after a while it became clear that preventing memory leaks entirely was unpractical in a language like rust, due to e.g. reference counting cycles or deadlocks or tons of different things

  • @Guru4hire
    @Guru4hire Рік тому +13

    Wouldn't you just use a unique_ptr in the c++ example and do essentially all the same thing?

    • @CryZe92
      @CryZe92 Рік тому +1

      unique_ptr is called unique for a reason. He would've had to create a (deep and expensive) copy of the vector to resolve the problem if he used unique_ptr (or vector). The solution would've been shared_ptr, but even that has a runtime cost, whereas in Rust it would've just been a completely free borrow and no unique_ptr / shared_ptr at all.

    • @Guru4hire
      @Guru4hire Рік тому +4

      You can create a std::unique_ptr and move it around to pass ownership or pass it by reference to allow borrowing of it. Its the point of unique_ptr. Its what it does.

    • @CryZe92
      @CryZe92 Рік тому +2

      @@Guru4hire Yeah but that misses the point of the example in the video. The example was that Bob had ownership and got destroyed and there was a dangling reference to the numbers still. unique_ptr wouldn‘t have helped here at all, unless you would‘ve moved out the numbers, but that‘s not what he wanted to do, he wanted to destruct Bob.

    • @Guru4hire
      @Guru4hire Рік тому

      I think I understand the point of disagreement now. I am saying that a unique_ptr to a class or struct bob which has a public unique_ptr to a vector of ints performs essentially the same as all the rust code examples. I would argue that the pathological get_n function (which is not in the rust example) in the c++ example would fail to compile as the unique_ptr's copy constructor is deleted. I would have liked to see how Rust handles the contrived use after free bug with the get_n function.

    • @dynfoxx
      @dynfoxx Рік тому

      @@Guru4hire one other thing is that C++ unique and shared is a runtime cost where Rust is a compile time check.
      C++ compiles down to pointers allocations and checks where rust just compiles to pointers.

  • @IMMACHARGINMYLAZOR
    @IMMACHARGINMYLAZOR Рік тому +1

    More rust content I love it a lot

  • @coder436
    @coder436 Рік тому +1

    1:14 does it need an immutable reference or a mutable reference?

  • @bradmartisius2625
    @bradmartisius2625 Рік тому +1

    When you have a class Bob in C++, the constructor is named Bob(arguments) & the destructor is named ~Bob(). The code shown in the video can't compile.

  • @m12652
    @m12652 2 місяці тому

    excellent talk, thanks very much 👍

  • @propov1802
    @propov1802 Рік тому +1

    Did anyone else notice that Bob's constructor and destructor had a different name

  • @rohankandi9900
    @rohankandi9900 Рік тому +4

    9:20 I would actually say the inverse here: at best the program crashes, at worst it gets some garbage. In my experience, debugging with garbage data has been much more hellish than immediately getting a seg fault and knowing the exact location of the problem.

  • @starlino
    @starlino Рік тому +1

    C++ arrays should be deleted with `delete[]` operator @ 6:04 , this is because over-allocation or an associative array technique is used to hold the number of elements in array, so you need to hint the compiler to de-allocate the latter too.

  • @sprightly106
    @sprightly106 Місяць тому

    You're a great teacher!

  • @frankhart2018
    @frankhart2018 Рік тому +1

    Thanks for the video. It would be nicer, if there were some program runs as well, like the garbage collection video :)

  • @andrycraft69
    @andrycraft69 Рік тому +3

    Completely unrelated question: why the numbers to the left of the code in the compiler are like that?

    • @mina86
      @mina86 Рік тому +3

      The one to the left is line number, the one to the right is distance from the current line. This lets you easily execute editor commands such us ‘go up N lines’ or ‘delete next N lines’.

    • @andrycraft69
      @andrycraft69 Рік тому +1

      @@mina86 Oh ok, that makes sense

  • @SoapSoapCrayon
    @SoapSoapCrayon Рік тому +2

    GC is the single worst cause of headaches in my job. I'm a senior programmer who works on video games, and I mostly deal with low level optimizations. An unreal GC collect call is going to cost 125ms on a switch. This is just for a call to GC.Collect, there might not even be any garbage to collect. Yes. that's 10 frames at 60 fps spent just looking for things to free. RAII amortizes these costs so they are hit at the moment they are freed. Spreading it out.

  • @x1expert1x
    @x1expert1x Рік тому

    19:49 where are you getting bob.n from? The value of bob is held in variable name b, not bob. is this just a typo you didn't notice?

  • @siggimund
    @siggimund Рік тому

    So, as a programming language and ferry enthusiast, was this interview recorded on the Dover/Calais or Dover/Dunkirk ferry connection? Hope I'll get through it without getting too seasick. 😁. Nah, sorry, that was a bikeshed comment. Very interesting and informative content actually👍

  • @LalliOni
    @LalliOni 6 місяців тому +1

    Great content, but a bit hard to follow. All the func_n examples introduce unneccesary cognitive load here. Also it would be great if it was being presented with live compiler messages. Showing exactly what the Rust compiler would be telling us if we were using an IDE.

  • @roz1
    @roz1 Рік тому +2

    I spotted a mistake in his code. The constructor and destructor should have the same name as the class name. Here name of class is Bob and you named the constructor and destructor as Foo

  • @danielpitts6913
    @danielpitts6913 Рік тому +1

    Yikes. At 4:53... The constructor should be called "Bob" since the class is "Bob". Also, you shouldn't use "this->n". It should be Bob(int x) : n(new int[x]) {}

    • @danielpitts6913
      @danielpitts6913 Рік тому

      Further yikes. At 5:45, the destructor doesn't use the correct delete operator, it should be "delete[] this->n"

  • @AntonAdelson
    @AntonAdelson Рік тому +1

    This is something I asked before but never got an answer.
    How does Rust handle asynchronous programming? I mean cases where you create an object but you must keep it in memory AFTER its scope runs out because it'll be used by the async function when it's ready???

    • @sumansaha295
      @sumansaha295 Рік тому

      I am not completely sure but an async function is converted into a finite state machine that is then handled by an async runtime like tokio. So the runtime does all the memory management. But it's very low overhead unlike garbage collectors.

    • @oracleoftroy
      @oracleoftroy Рік тому

      Not a Rust programmer (as a C++ guy I've been keeping my eye on it and messed with it in small programs), so I might miss the finer details, but you either move the memory into the async function so that the owner (and thus the responsibility of releasing it) is transferred, or if multiple functions need ownership, you use a reference counted shared pointer (Rc or Arc, I forget which one is appropriate for multi-threading). Or you redesign your algorithm to not have this situation in the first place, as any sort of sharing tends to be bad for concurrency in general.

    • @OrbitalCookie
      @OrbitalCookie Рік тому

      From simplest to complex: pass object when creating a thread, get the result when the thread finishes; wrap data in Mutex to access it from multiple threads; use channels to send data between threads; use async/await to run many things concurrently on an executor that handles threading (this is mostly used for I/O tasks).

    • @OrbitalCookie
      @OrbitalCookie Рік тому +1

      Forgot the last one: write your own mechanism like channels using unsafe rust and raw pointers that has a safe rust api surface and can't be misused. Some say it's very advanced and not for newbies, but if you want freedom to shoot yourself in the foot, rust rivals and surpasses C++ in this area.

    • @AntonAdelson
      @AntonAdelson Рік тому

      @@OrbitalCookie Wait, what? So there are unsafe raw pointers? Is it just syntaxis sugar to use them or something more complicated?

  • @cinemabaroque
    @cinemabaroque Рік тому

    With more than 2 million subscribers, I hope you can get a tripod soon.

  • @OgnyanManchev
    @OgnyanManchev Рік тому +1

    This video is way below Computerphile standards. In your series the presenter dives so smoothly into the foundations of the matter and explains the core logic behind for total n00bs. All I understood from this video is how cool Rust is because it's the same as C++, but opposite. There must be a reason it's so popular, but the video failed to convey it.

  • @jgricourt
    @jgricourt 3 місяці тому

    The C++ code given as an example here compiles fine (change the name "Foo" for "Bob"). It shows clearly that you can mess up things easily in C++ and other traditional languages. I know that there are now better ways of writing this code in modern C++ to avoid pitfalls, but the point here is to show how safety tightly bound into the language itself can address these quirks, but I admit a better programmer can do as well ...

  • @sebsplatter914
    @sebsplatter914 Рік тому

    Great video, really helpful! The comments are already picking apart all the technicalities in classic comment section fashion, so I will add some small video editing feedback: at 12:19 for example you pull up screenshots of the code that is being referenced by the speaker, which is great, but I would prefer if it wasnt stretched in such a funky way. It makes it seem dynamic but it also makes the "backwards" parts of it hard to read on small screens. Thanks for the work!

  • @javib8970
    @javib8970 Рік тому

    THANK YOU! this is the first coherent video explaining rust differences with c ive seen so far .
    You got deeper than "woa is so cool use rust IS the future use It use It use It"

    • @TheJaguar1983
      @TheJaguar1983 Рік тому +3

      Except that the C++ example was completely wrong and was designed to make Rust look much more superior than it really is.

    • @javib8970
      @javib8970 Рік тому

      @@TheJaguar1983 why IS everyone pushing It? Are they getting paid? Are masons behind rust?

  • @SqueakyNeb
    @SqueakyNeb Рік тому +3

    Writing C-with-classes and calling it C++ (in that you didn't use std::vector, which is the proper approach to this code) is a bit of a hatchet job. What Rust has "built into the language" is literally right there in C++ just the same.
    I know examples are usually contrived but like damn dude.

  • @HaouasLeDocteur
    @HaouasLeDocteur Рік тому +1

    8:40 why use ``new``? That kinda goes against the whole RAII thing. Should have had Bob as an automatic object on the stack so that when you leave that scope its destructor is called without you needing to ``delete`` it. In that case, even the dangling pointer may have been avoided.

  • @novasurfer
    @novasurfer Рік тому +5

    Okay, but it's not C++. No one writing programs like that in real life.
    There are tools which will help you to find different kinds of errors.
    Clang-tidy, Valgrind, PVS Studio, compiler flags like `-fsanitize=address`, maybe something for MSVC from Microsoft.
    Clang-tidy, can analyze code in real time, it's easy to use, and built in in CLion IDE, can be easy installed in Vim/Emacs with a help of LSP and clang tools.
    And of course there are unique pointers and move-semantics since 2011. Rust is cool, but C++ does not stand still.

  • @AU-hs6zw
    @AU-hs6zw Рік тому

    Thank you!. It is a great video.

  • @MrTickely
    @MrTickely Рік тому

    Glad to see the GOAT language getting some love on the channel - hope more rust content is coming :)

  • @sumansaha295
    @sumansaha295 Рік тому +2

    I like rust but there are no large well known projects with it yet which makes me a bit anxious about the practical applicability of the language given how strict it is with everything.

    • @dynfoxx
      @dynfoxx Рік тому +1

      While Rust does not have any big user facing killer apps, you are or most likely will be using it within the next year.
      Firefox, cloudflare and Android already uses it. Microsoft, Apple and Google have picked it up(may already use it). Linux and Chrome have are adding support for Rust.
      While Rust is still getting features and is not perfect for every project there is no doubt that it is a viable programming language.

    • @Kuratius
      @Kuratius Рік тому

      ​​​@@dynfoxx Firefox/Mozilla are the ones that made rust and they ultimately decided against using it for the thing they invested into it for: servo.
      There are still some components of Firefox in Rust, but the most performance critical component isn't and probably never will be.

  • @pheww81
    @pheww81 Рік тому +2

    if you do a new[] please do a delete[]. Even in a so simple example bug has creep in. Furthers proof that most programmers should not write this kind of code themself.

    • @toby9999
      @toby9999 Рік тому +1

      It's pretty basic stuff that any half decent programmer should get right. It bugs me when people blame such things on the language. Like blaming a car for driving the wrong way down a one-way street.

  • @real1cytv
    @real1cytv Рік тому

    I think something that was a little left out ist that you can do most things with rusts RAII principles (except for multiple owners, so reference counting). If you want to free some memory halfway through an objects lifetime, you can give the Memory to an `Option` which does runtime checks on the variables validity, which your Object then holds onto. This then forces users of the object to consider whether or not the memory is valid at that current time. In rust you very rarely actually need `unsafe` blocks, unless you're doing something like embedded programming or unsafe magic.
    Also rusts reference counting doesn't actually violate the one owner principal, since the reference counted "backend" owns the original data (in implementation this isn't quite correct, there is an UnsafeCell backing all of this, but for the users purpose this doesn't matter)

  • @spik330
    @spik330 Рік тому

    One of the things I have never understood about rust is how to do something like a read write queue. There are many cases were we pass immutable as a way to create "Read-only" memory for a part of the program but not that its immutable. By this logic, we can easily make a concurrency queue and pass it to all the workers, but any attempts add any jobs will then be stopped as you would be mutating a queue which has borrowed references.

    • @KohuGaly
      @KohuGaly Рік тому

      The thing you are missing is that the mutable vs immutable reference in Rust is a misnomer. What they actually are is unique vs shared reference. It is possible to create types that can be mutated through a shared reference. A prime example of this is mutex.

  • @MrMediator24
    @MrMediator24 Рік тому +2

    Waited for a quite a while to hear "Rust isn't a niche language". Also it has name for it's memory management system - OBRM (Object Based Resource Management)

  • @Rick.Fleischer
    @Rick.Fleischer Рік тому +2

    In C++, aren't constructors and destructors required to have the same name as the class?