C++ 为什么我不能分配给uint_8[]类型的unique_ptr?

C++ 为什么我不能分配给uint_8[]类型的unique_ptr?,c++,C++,考虑一下,我已经初始化了独特的ptr,如下所示: unique_ptr<uint_8[]> pixels{nullptr}; 不幸的是,它不允许分配大小为10*8的新数组。 我知道,我可以简单地分配std::make_unique10,但我只想了解智能指针 因此,基本上,问题是: 为什么不允许从nullptr强制转换到新阵列? nullptr是C++11中的某种特定类型吗? 这意味着将使用运算符=of std::unique_ptr。但是,如果查看all operator=您将注意

考虑一下,我已经初始化了独特的ptr,如下所示:

unique_ptr<uint_8[]> pixels{nullptr};
不幸的是,它不允许分配大小为10*8的新数组。 我知道,我可以简单地分配std::make_unique10,但我只想了解智能指针

因此,基本上,问题是:

为什么不允许从nullptr强制转换到新阵列? nullptr是C++11中的某种特定类型吗? 这意味着将使用运算符=of std::unique_ptr。但是,如果查看all operator=您将注意到std::unique_ptr的T*没有重载

将调用您需要的方法,并将存储在std::unique_ptr中的旧值重置为新值:

pixels.reset(new uint_8[10]);
这意味着将使用运算符=of std::unique_ptr。但是,如果查看all operator=您将注意到std::unique_ptr的T*没有重载

将调用您需要的方法,并将存储在std::unique_ptr中的旧值重置为新值:

pixels.reset(new uint_8[10]);

嗯,如果我错了,请纠正我,但是OP问如何分配。这是一个非常具体的问题,也有一个非常具体的标题。OP需要的方法可能不是重置

// replaces the current payload with the new empty one
pixels.reset(new uint_8[10]);
如果我没有混淆要指定的术语的含义,那么上面的内容似乎没有指定任何像素

我大胆地假设以下内容可能符合询问者的喜好:

// array of uint8_t elements
using u8arr = std::uint8_t[];

// instance of the said array
// that contains 3 uint8 values
u8arr uar{0,1,2};

// declare unique_ptr to the same array type
std::unique_ptr<u8arr> smart_arr_;

// at last ! we assign to the "smart array"
assign(smart_arr_, uar);

// the proof of the pudding
::wprintf(L"\n\n%d\t%d\t%d", smart_arr_[0],smart_arr_[1],smart_arr_[2]);
就像变魔术一样,我有一个我之前准备好的assign ready的实现:

template<typename C, size_t N>
inline auto 
    assign
(
    std::unique_ptr<C[]> & sp_,
    const C(& arr)[N]
) noexcept
    -> std::unique_ptr<C[]> &
{
    static_assert(std::is_trivially_copyable_v<C>);
    sp_.release();
    sp_ = std::make_unique<C[]>(N + 1);
    void * rez_ = ::memcpy(sp_.get(), arr, N);
    assert(rez_);
    return sp_;
}

为了确保好的旧memcpy不会反对,我使用了static_断言来检查要复制的类型

嗯,如果我错了,请纠正我,但是OP问如何分配。这是一个非常具体的问题,也有一个非常具体的标题。OP需要的方法可能不是重置

// replaces the current payload with the new empty one
pixels.reset(new uint_8[10]);
如果我没有混淆要指定的术语的含义,那么上面的内容似乎没有指定任何像素

我大胆地假设以下内容可能符合询问者的喜好:

// array of uint8_t elements
using u8arr = std::uint8_t[];

// instance of the said array
// that contains 3 uint8 values
u8arr uar{0,1,2};

// declare unique_ptr to the same array type
std::unique_ptr<u8arr> smart_arr_;

// at last ! we assign to the "smart array"
assign(smart_arr_, uar);

// the proof of the pudding
::wprintf(L"\n\n%d\t%d\t%d", smart_arr_[0],smart_arr_[1],smart_arr_[2]);
就像变魔术一样,我有一个我之前准备好的assign ready的实现:

template<typename C, size_t N>
inline auto 
    assign
(
    std::unique_ptr<C[]> & sp_,
    const C(& arr)[N]
) noexcept
    -> std::unique_ptr<C[]> &
{
    static_assert(std::is_trivially_copyable_v<C>);
    sp_.release();
    sp_ = std::make_unique<C[]>(N + 1);
    void * rez_ = ::memcpy(sp_.get(), arr, N);
    assert(rez_);
    return sp_;
}

为了确保好的旧memcpy不会反对,我使用了static_断言来检查要复制的类型

nullptr是C++11中的某种特定类型吗?它是std::nullptr\t,但我看不出这有什么关系。你能展示一下你从nullptr转换到新数组的代码吗?你很可能想使用。重置unique\ptr。但是,如果没有确切的错误消息,就不能说,您应该将其包含在问题中。强制转换意味着涉及某种显式的新类型,例如,将nullptr强制转换为int*。您正在执行赋值,而不是强制转换。@chris您正在进行赋值,但由于new和std::unique_ptr是两种不同的类型,GNU编译器也尝试将new强制转换为std::unique_ptr,因此它会为std::unique_ptr类型抛出一个错误,并为std::unique_ptr newIs nullptr在C++11中的某个特定类型抛出一个缺失的=重载?它是std::nullptr\t,但我看不出这有什么关系。你能展示一下你从nullptr转换到新数组的代码吗?你很可能想使用。重置unique\ptr。但是,如果没有确切的错误消息,就不能说,您应该将其包含在问题中。强制转换意味着涉及某种显式的新类型,例如,将nullptr强制转换为int*。您正在执行赋值,而不是强制转换。@chris您正在进行赋值,但由于new和std::unique_ptr是两种不同的类型,GNU编译器也尝试将new强制转换为std::unique_ptr,因此它会为std::unique_ptr类型抛出一个错误和一个missing=重载,我想是的。因此,只有当右边是nullptr或std::unique\u ptr,并且std::make\u unique是unique\u ptr的一种类型时,它才会重载?@AlisherKassymov不是真的,unique\u ptr不能复制,只能移动。nullptr是一种特殊情况,类似于调用reset。另一个重载接受r值引用,即移动的唯一\u ptr。@AlisherKassymov如果使用std::make_unique,则会发生接受唯一\u ptr&&的重载。基本上,右边应该是null ptr或std::unique\u ptr类型的右值,因为std::unique\u ptr意味着独占所有权。是的,我仔细检查了它并看到了&&。我想这就是为什么它是独一无二的;谢谢mate@AlisherKassymov名字中的暗示是:好的,我想是的。因此,只有当右边是nullptr或std::unique\u ptr,并且std::make\u unique是unique\u ptr的一种类型时,它才会重载?@AlisherKassymov不是真的,unique\u ptr不能复制,只能移动。nullptr是一种特殊情况,类似于调用reset。另一个重载接受r值引用,即移动的唯一\u ptr。@AlisherKassymov如果使用std::make_unique,则会发生接受唯一\u ptr&&的重载。基本上,右边应该是null ptr或std::unique\u ptr类型的右值,因为std::unique\u ptr意味着独占所有权。是的,我仔细检查了它并看到了&&。我想这就是为什么它是独一无二的;谢谢mate@AlisherKassymov名字里的暗示 :