News for hackers. Stuff that matters.
Re:The missing C++ smart pointer by assbuttbuttass on Sunday August 20, 2023 @03:03PM (#37202012)
I'm not sure I see the benefit vs std::unique_ptr. In the rare case you do want to deep-copy a unique_ptr, you can always use std::make_unique() to invoke the copy constructor
Re:The missing C++ smart pointer by seeknotfind on Sunday August 20, 2023 @03:15PM (#37202102)
Kind of, though because the language does a lot of things for you when you use the built in copy, make_unique gets complicated when you want to use std::box inside of another structure. You would need to override the default copy constructor to get this to work. For instance, vector<box<Foo>> wouldn't be possible to implement with unique_ptr because you can't override the copy constructor for a templated type. std::box would allow you to copy it. As for why you would need to do this (over vector<Foo>), consider Foo having subclasses. Complexity breeds complexity...

Regardless, I think lifetime annotations would solve far more problems than std::box. I really do like box as a suggestion as it would help clean up types, make things a bit more explicit in a few places, but there are bigger issues with C++ right now. This is a great suggestion (as is unique_resource for similar on the stack), but a relatively minor thing in the scheme of things. Still nice.

Re:The missing C++ smart pointer by pjmlp on Sunday August 20, 2023 @04:20PM (#37202591)
Lifetime annotations are somehow complicated without subseting the language.

It isn't as if Microsoft, Apple and Google haven't been doing it for a while.

https://devblogs.microsoft.com/cppblog/high-confidence-lifet...

https://reviews.llvm.org/D15032

Re:The missing C++ smart pointer by LegionMammal978 on Sunday August 20, 2023 @03:08PM (#37202058)
That was my thought as well; even Rust requires a .clone() call to deep-copy a Box<T>, since it doesn't allow implicit copies of types without the Copy trait. (Types with that trait must effectively be "plain old data" that can be copied byte-by-byte.) So I don't see the issue with requiring an explicit copy function for std::unique_ptr<T> instead of an implicit copy constructor.
Re:The missing C++ smart pointer by ithkuil on Sunday August 20, 2023 @03:19PM (#37202150)
But if you clone a struct that contains a Box<T> field then that field is also cloned (at least that's the behavior if the default derived Clone impl)
Re:The missing C++ smart pointer by loeg on Sunday August 20, 2023 @03:19PM (#37202148)
Yeah, this is just a unique_ptr with a copy operation.
Re:The missing C++ smart pointer by nemetroid on Sunday August 20, 2023 @05:07PM (#37202932)
You could make a similar argument about std::unique_ptr, that you can always use new and delete to create and destroy.

Which one of these (which implement the same copy/move semantics) would you prefer?

  struct A {
      box<int> thing;
  }

  struct B {
      std::unique_ptr<int> thing;
      B(std::unique_ptr<int> t) :
      thing(std::move(t))
      {}
      B(const B& other) :
        thing{std::make_unique<int>(*other.thing)}
        {}
      B& operator=(const B& other) {
          thing = std::make_unique<int>(*other.thing);
          return *this;
      }
      B(B&&) = default;
      B& operator=(B&&) = default;
      ~B() = default;
  };
Re:The missing C++ smart pointer by fluoridation on Sunday August 20, 2023 @05:36PM (#37203140)
Personally, I've never needed to copy something that was both not trivially copiable and the component parts of which were individually trivially copiable. If thing just gets initialized immediately, why do you put it in a pointer? Usually you would put it in a pointer because you need to initialize it in a specific order in the constructor relative to the other members (so presumably also in the copy constructor), or because it's a polymorphic object (so you can't just use the copy constructor of the static type). If neither of those is true, why use a pointer at all? Just make the member a simple object.
Re:The missing C++ smart pointer by nemetroid on Sunday August 20, 2023 @05:53PM (#37203267)
Types that are self-referential in one way or another, e.g. a graph where nodes point to each other, or a "main object" containing subobjects which point back to the main object. There is no way to implement an efficient move for such types (it would need to adjust all pointers), so implementing move operations would be misleading. If you want to be able to pass around ownership of such a type, it needs to happen through pointer indirection.

But you might want to allow a copy operation that recreates the entire structure. The proposed box<T> offers exactly the desired copy/move semantics.

Re:The missing C++ smart pointer by adrian_b on Monday August 21, 2023 @12:28AM (#37205500)
It can be argued that any types like those described by you are wrongly designed.

For a self-referential type like a graph, either a value of the graph is completely stored in a contiguous region of memory, including all nodes, when the self-references should not be pointers, but offsets from the start of the region, and a graph value can be moved or copied anywhere without problems, or else a graph value consists only of a list of pointers, which point to node contents without pointers, which are scattered through the memory. In the second case, a graph value, i.e. the list of pointers, can also be copied or moved anywhere in the memory without any problems, like you would do with any single pointer.

Mixing pointers with data makes sense only for objects with embedded pointers whose purpose is to allow them to be inserted in linked links or trees, where such objects will never be copied or moved, but only created and destroyed.

Re:The missing C++ smart pointer by fluoridation on Tuesday August 22, 2023 @05:58AM (#37220600)
Those sorts of types fail the second requirement. The members are not trivially copyable on their own because they contain tremendous structure that may only be discernible at the top level. A generic box pointer doesn't help you there because the problem is not implementing the copy methods of the members, but implementing the copy method of the outermost object.
Re:The missing C++ smart pointer by Asooka on Sunday August 20, 2023 @05:34PM (#37203125)
Huh, isn't struct B literally what an implementation of std::box would look like? You would need a nullptr check in the copy ctor and copy assignment operator to make it complete, but other than that, that is exactly how I would implement box. Anything that would be in std, you can implement yourself, so I would encourage people to try implementing box themselves and see how it works for them.
Re:The missing C++ smart pointer by nemetroid on Sunday August 20, 2023 @06:04PM (#37203344)
Yes, it's not too difficult (but thanks for the pointer, edited). The question was why this smart pointer would be useful at all, not just whether it belongs in the standard library. Implementing the helper class yourself is not too bad, but putting this in domain classes is a lot of cruft.