У меня проблема, которая возникает только в моем полном коде. Как вы можете видеть ниже, я изолировал его до минимально воспроизводимого примера:
#include <iostream>
#include <string>
#include <memory>
class GenericObjectHolder
{
public:
GenericObjectHolder()
{
}
virtual ~GenericObjectHolder() = 0;
};
template <class T, class Holder = GenericObjectHolder>
//Final because we shouldn't allow destructor to be overriden
//because we absolutely must delete the holder
//TODO: can child class call parent class's destructor????
class Buffer final
{
public:
//Ownership WILL be passed to this object
static Buffer fromOwned(T buffer, size_t size)
{
return Buffer(std::make_unique<T>(buffer), size);
}
//Creates a buffer from an object that holds the buffer
//ownership and saves the object too so it's only destructed
//when this buffer itself is destructed
static Buffer fromObject(T buffer, size_t size, Holder *holder)
{
return Buffer(std::make_unique<T>(buffer), size, holder);
}
//Allocates a new buffer with a size
static Buffer allocate(size_t size)
{
return Buffer(std::make_unique<T>(new T[size]), size);
}
/*
Buffer &operator=(const Buffer & buffer)
{
_size = buffer._size;
_holder = buffer._holder;
_buffer = std::move(buffer._buffer);
}
*/
~Buffer()
{
if (_holder)
delete _holder;
}
//TODO: read this and think
virtual void consumed(size_t amountConsumed)
{
//_buffer += amountConsumed;
_size -= amountConsumed;
}
virtual T *data()
{
return _buffer.get();
}
virtual size_t size() const
{
return _size;
}
Buffer(std::unique_ptr<T> buffer, size_t size)
{
_buffer = std::move(buffer);
_size = size;
}
Buffer(std::unique_ptr<T> buffer, size_t size, Holder *holder)
{
_buffer = std::move(buffer);
_size = size;
_holder = holder;
}
Buffer(const Buffer &buffer) : _size(buffer._size),
_holder(buffer._holder)
{
_buffer = std::move(buffer._buffer);
}
private:
Holder *_holder;
std::unique_ptr<T> _buffer;
size_t _size = 0;
};
int main()
{
auto b = Buffer<uint8_t*, GenericObjectHolder>::fromOwned(new uint8_t[1], 1);
}
, но он прекрасно компилируется .
В моей библиотеке я получаю:
/workspaces/libopenvpnclient/src/AsioAsyncChannel.h:98:21: error: overload resolution selected deleted operator '='
_buffer = std::move(buffer._buffer);
~~~~~~~ ^ ~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/lib/gcc/x86_64-linux-gnu/9/../../../../include/c++/9/bits/unique_ptr.h:415:19: note: candidate function has been explicitly deleted
unique_ptr& operator=(const unique_ptr&) = delete;
^
/usr/lib/gcc/x86_64-linux-gnu/9/../../../../include/c++/9/bits/unique_ptr.h:305:7: note: candidate function not viable: 1st argument ('typename std::remove_reference<const unique_ptr<unsigned char *, default_delete<unsigned char *> > &>::type' (aka 'const std::unique_ptr<unsigned char *, std::default_delete<unsigned char *> >')) would lose const qualifier
operator=(unique_ptr&& __u) noexcept
^
/usr/lib/gcc/x86_64-linux-gnu/9/../../../../include/c++/9/bits/unique_ptr.h:325:2: note: candidate template ignored: deduced type 'unique_ptr<...>' of 1st parameter does not match adjusted type 'unique_ptr<...>' of argument [with _Up = unsigned char *, _Ep = std::default_delete<unsigned char *>]
operator=(unique_ptr<_Up, _Ep>&& __u) noexcept
^
/usr/lib/gcc/x86_64-linux-gnu/9/../../../../include/c++/9/bits/unique_ptr.h:334:7: note: candidate function not viable: no known conversion from 'typename std::remove_reference<const unique_ptr<unsigned char *, default_delete<unsigned char *> > &>::type' (aka 'const std::unique_ptr<unsigned char *, std::default_delete<unsigned char *> >') to 'std::nullptr_t' (aka 'nullptr_t') for 1st argument
operator=(nullptr_t) noexcept
^
и в обоих случаях я использую Clang 10.
Кто-нибудь знает, почему это происходит?
Я не понимаю, почему он жалуется на то, что я назначаю a unique_ptr
в буфер, так как я его перемещаю. Вы также можете видеть, что я прокомментировал оператор присваивания. Я попытался использовать его, но он пожаловался на то, что у меня нет оператора копирования.