Date: Tue, 13 Jun 2023 12:44:00 +0200
On 2023-06-13 at 10:34, Federico Kircheis via Std-Proposals wrote:
>
> Hello to everyone, please consider following snippet
>
> ----
> #include <vector>
> #include <memory>
>
> struct s{
> std::vector<std::unique_ptr<int>> d;
> };
>
> static_assert(!std::is_copy_assignable<std::unique_ptr<int>>::value);
> static_assert(std::is_copy_assignable<std::vector<std::unique_ptr<int>>>::value);
> static_assert(std::is_copy_assignable<s>::value);
>
> void bar(){
> s s1;
> // fails, as expected, but inconsistent with is_copy_assignable
> auto s2 = s1;
> }
> ----
This isn't copy assignment, but copy construction. But anyway.
>
> Doesn't the second static_assert bother anyone?
>
> Vector is always is_copy_assignable, but in fact it is a compile-time
> error (auto s2 = s1) does not compile.
The vector is copy assignable, because it has a copy assignment
operator. That's what the test tells us.
The fact that the implementation then fails to compile for some types,
is a different question. The type trait doesn't check the body of the
operator, just its presence.
>
> Depending on the compiler, compiler errors are also verbose
> (https://godbolt.org/z/3E49c4oT7) and not necessarily easy to understand
> (immagine if s is part of a class hierarchy or a member of another
> class...)
>
> An improvement for the end-user is to delete the copy-constructor of s
> by hand, it does not change what programs are valid, but the error
> message is much more easy to understand.
>
> But it does not fix the underlying issue, and the fact that one cannot
> simply follow the "rule of 0" and let the compiler use the defaulted
> copy and move constructors without writing them down.
>
> Does anyone know if there is already a paper trying to fix this issue,
> or if there was one and was rejected?
> I assume the main difficulty is specifying something that also works
> with forward-declared types.
>
>
> Hello to everyone, please consider following snippet
>
> ----
> #include <vector>
> #include <memory>
>
> struct s{
> std::vector<std::unique_ptr<int>> d;
> };
>
> static_assert(!std::is_copy_assignable<std::unique_ptr<int>>::value);
> static_assert(std::is_copy_assignable<std::vector<std::unique_ptr<int>>>::value);
> static_assert(std::is_copy_assignable<s>::value);
>
> void bar(){
> s s1;
> // fails, as expected, but inconsistent with is_copy_assignable
> auto s2 = s1;
> }
> ----
This isn't copy assignment, but copy construction. But anyway.
>
> Doesn't the second static_assert bother anyone?
>
> Vector is always is_copy_assignable, but in fact it is a compile-time
> error (auto s2 = s1) does not compile.
The vector is copy assignable, because it has a copy assignment
operator. That's what the test tells us.
The fact that the implementation then fails to compile for some types,
is a different question. The type trait doesn't check the body of the
operator, just its presence.
>
> Depending on the compiler, compiler errors are also verbose
> (https://godbolt.org/z/3E49c4oT7) and not necessarily easy to understand
> (immagine if s is part of a class hierarchy or a member of another
> class...)
>
> An improvement for the end-user is to delete the copy-constructor of s
> by hand, it does not change what programs are valid, but the error
> message is much more easy to understand.
>
> But it does not fix the underlying issue, and the fact that one cannot
> simply follow the "rule of 0" and let the compiler use the defaulted
> copy and move constructors without writing them down.
>
> Does anyone know if there is already a paper trying to fix this issue,
> or if there was one and was rejected?
> I assume the main difficulty is specifying something that also works
> with forward-declared types.
>
Received on 2023-06-13 10:44:13