智能指针(unique_ptr)自定义删除器错误C2027和C2338

问题描述 投票:0回答:1

我尝试将智能指针与SDL2一起使用,并且需要一个自定义删除器。我使用此代码并收到错误C2027(使用未定义的SDL_Texture类型)和C2338(无法删除不完整的类型)

ftexture = std::make_unique<SDL_Texture>(TTF_RenderText_Solid(font, fontData.c_str(), fontColor),
        [=](SDL_Texture* texture) {SDL_DestroyTexture(texture); });

我班上的这个变量看起来像这样:

std::unique_ptr <SDL_Texture> ftexture = nullptr;
c++ sdl smart-pointers sdl-2
1个回答
4
投票

首先,TTF_RenderText_Solid()返回SDL_Surface*,而不是SDL_Texture*SDL_Surface并非源自SDL_Texture

其次,您不能使用std::make_unique()指定自定义删除器。第一个模板参数用作结果Tstd::unique_ptr类型,其余模板参数用作输入参数,这些参数都传递给T的构造函数。在您的示例中,TSDL_Texture,并且没有SDL_Texture的构造函数采用SDL_Surface*和lambda作为输入。

要使用自定义删除器,需要将删除器的类型指定为std::unique_ptr的模板参数,std::make_unique()不允许这样做,因此必须直接使用std::unique_ptr

删除程序应该是单独的类型,而不是lambda:

struct SDL_Surface_Deleter
{
    void operator()(SDL_Surface* surface) {
        SDL_FreeSurface(surface);
    } 
};

using SDL_Surface_ptr = std::unique_ptr<SDL_Surface, SDL_Surface_Deleter>;
SDL_Surface_ptr fsurface;

...

fsurface = SDL_Surface_ptr(
    TTF_RenderText_Solid(font, fontData.c_str(), fontColor)
);

但是,如果您确实想使用lambda,则可以执行以下操作:

using SDL_Surface_Deleter = void (*)(SDL_Surface*);
using SDL_Surface_ptr = std::unique_ptr<SDL_Surface, SDL_Surface_Deleter>;
SDL_Surface_ptr fsurface;

...

fsurface = SDL_Surface_ptr(
    TTF_RenderText_Solid(font, fontData.c_str(), fontColor),
    [](SDL_Surface* surface) { SDL_FreeSurface(surface); }
);

或者,您可以直接将SDL_FreeSurface()用作实际的删除器:

using SDL_Surface_ptr = std::unique_ptr<SDL_Surface, decltype(&SDL_FreeSurface)>;
SDL_Surface_ptr fsurface;

...

fsurface = SDL_Surface_ptr(
    TTF_RenderText_Solid(font, fontData.c_str(), fontColor),
    &SDL_FreeSurface
);
© www.soinside.com 2019 - 2024. All rights reserved.