New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add std::unique_ptr support to gsl::span #404
Conversation
@rianquinn I like Jonathan Wakeley's paper, but I don't think there's any need to delay adding support for |
That's fine. There a couple of issues (some are just things I have to learn about template programming).
|
@neilmacintosh I added support for std::shared_ptr. I actually had it backwards and needed to add a reference to unique_ptr so all around I think this is better. Sadly, I left my editor in a mode were it removed trailing spaces, which I guess is in issue in the code. If you want, I can re-submit this with the spaces added back in. Up to you. |
I fixed the whitespace issue, so we should be good to go. |
967ddb5
to
c221450
Compare
Any other comments on this PR? |
I'll take a look a little later on today. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for putting this together @rianquinn! I've left a few comments.
{ | ||
{ | ||
auto arr = new int[4]; | ||
auto ptr = std::unique_ptr<int>(arr); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Doesn't this result in the wrong delete
being called when ptr
goes out of scope?
arr[i] = i + 1; | ||
|
||
{ | ||
span<int> s{arr, 4}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is arr
here supposed to be ptr
? I assumed you were trying to test construction of the span
from the unique_ptr
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
oppsss. nice catch
} | ||
|
||
{ | ||
span<int> s{std::unique_ptr<int>{nullptr}, 0}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
While I get that it's probably ok in this exact test case, it seems like it might encourage a misunderstanding to construct a span
from a temporary unique_ptr
. For any initial value other than nullptr
that would result in disaster ;-)
} | ||
|
||
{ | ||
span<int> s{std::unique_ptr<int>{nullptr}, 0}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As per previous comment, container lifetime must always exceed view lifetime.
} | ||
|
||
{ | ||
span<int> s{std::unique_ptr<int>{nullptr}, 0}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm assuming this should be shared_ptr
, not unique_ptr
, but then it should also outlive the span
created from it.
TEST(from_shared_pointer_construction) | ||
{ | ||
auto arr = new int[4]; | ||
auto ptr = std::shared_ptr<int>(arr); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm pretty sure this will use the wrong delete
unless you provide a custom deleter argument.
@@ -386,6 +387,11 @@ public: | |||
{ | |||
} | |||
|
|||
template<class ArrayElementType = std::add_pointer<element_type>> | |||
constexpr span(const std::unique_ptr<ArrayElementType>& ptr, index_type count) : storage_(ptr.get(), count) {} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
My feeling is that we want two constructors here, to distinguish between the array and non-array holding versions of unique_ptr'. The non-array version doesn't need a count, it can just be a convenient way to initialize a single-element
span` from that particular standard container.
template<class ArrayElementType = std::add_pointer<element_type>> | ||
constexpr span(const std::unique_ptr<ArrayElementType>& ptr, index_type count) : storage_(ptr.get(), count) {} | ||
|
||
constexpr span(const std::shared_ptr<ElementType>& ptr, index_type count) : storage_(ptr.get(), count) {} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Until shared_ptr
can officially take multiple elements, I'd be tempted to just have this constructor take a shared_ptr
and construct a single-element span
from it. If we hear that a lot of people go to the effort of putting dynamically-allocated arrays into shared_ptr
, then we can always add the second overload.
This patch adds support for std::unique_ptr and std::shared_ptr to the gsl::span class instead of having to manually grab the pointer via get(). For reference, this is part of the following issue: microsoft#402 Signed-off-by: “Rian <“rianquinn@gmail.com”>
c221450
to
dd2d57a
Compare
@neilmacintosh Thanks for the awesome feedback. Sorry it took so long to get the fixes in. I think this patch addresses all of your concerns, and I agree that this is a much cleaner approach as the non-array versions make a lot more sense this way. |
Thanks @rianquinn, this is a nice addition to the group of standard library containers supported by |
This patch adds support for std::unique_ptr to the gsl::span
class instead of having to manually grab the pointer from
a std::unique_ptr.
It was suggestd that we also add support for std::shared_ptr,
but no array syntax exists for this class, and the element
types don't match. Until the following is accepted, I suggest
support for std::shared_ptr is left out:
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4077.html
For reference, this is part of the following issue:
#402
Signed-off-by: “Rian <“rianquinn@gmail.com”>