Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/ms-access/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如何避免使用插入迭代器调用复制构造函数 模板 void BlitSurface::提取帧(输出它, 整数帧宽度,整数帧高度, 每行整数帧,每列整数帧, 布尔填充)常数 { SDL_表面**temp_surf=SDL_Ex_ExtractFrames(_表面、框架宽度、框架高度、每行框架、每列框架、填充); int surface_count=每行帧数*每列帧数; 对于(int i=0;i_C++_Iterator_Containers_Insert Iterator - Fatal编程技术网

C++ 如何避免使用插入迭代器调用复制构造函数 模板 void BlitSurface::提取帧(输出它, 整数帧宽度,整数帧高度, 每行整数帧,每列整数帧, 布尔填充)常数 { SDL_表面**temp_surf=SDL_Ex_ExtractFrames(_表面、框架宽度、框架高度、每行框架、每列框架、填充); int surface_count=每行帧数*每列帧数; 对于(int i=0;i

C++ 如何避免使用插入迭代器调用复制构造函数 模板 void BlitSurface::提取帧(输出它, 整数帧宽度,整数帧高度, 每行整数帧,每列整数帧, 布尔填充)常数 { SDL_表面**temp_surf=SDL_Ex_ExtractFrames(_表面、框架宽度、框架高度、每行框架、每列框架、填充); int surface_count=每行帧数*每列帧数; 对于(int i=0;i,c++,iterator,containers,insert-iterator,C++,Iterator,Containers,Insert Iterator,,提到正在调用一个复制构造函数。在提供的示例中,容器似乎被定义为保存BlitSurface。类似于std::vector。这是我从以下几行中的猜测: for(int i=0; i<surface_count; ++i) { it->_surface = temp_surf[i]; ++it; } 我的理解是,所有std容器都会在插入时进行复制。从那时起,您可以通过引用使用容器中的对象。如果您不希望在BlitSurface上调用复制构造函数,那么我建议容器存储指向Bl

,提到正在调用一个复制构造函数。在提供的示例中,容器似乎被定义为保存BlitSurface。类似于std::vector。这是我从以下几行中的猜测:

for(int i=0; i<surface_count; ++i)
{
    it->_surface = temp_surf[i];
    ++it;
}
我的理解是,所有std容器都会在插入时进行复制。从那时起,您可以通过引用使用容器中的对象。如果您不希望在BlitSurface上调用复制构造函数,那么我建议容器存储指向BlitSurface的指针。这样,当容器在插入obje时进行复制时它实际上复制的ct是一个指针(不是指向的BlitSurface对象)


请记住,这种方法在堆上分配内存(即新的),因此以后必须显式删除内存,或者可以在容器中使用某种类型的智能指针来处理删除(std::vector>).

实际上,您需要的是一个与插入输出迭代器一起使用的移动输入迭代器。由于C++03中不存在该迭代器,因此需要另一种方法来表示需要“浅”移动,而不是“深”复制

对象本身中的简单状态标志不起作用,因为允许实现在实际将对象放入容器之前随机复制对象(为了优化,您知道它不会,但最好不要担心调试构建)

不经意间,这听起来像是定制分配器的工作。默认分配器使用placement new复制构造;您可以定义一个替代构造函数,并使用placement new调用它

    BlitSurface* bs = new BlitSurface;
    bs->_surface = temp_surf[i];
    *it = bs;
模板
结构移动特性{
typedef T must_copy_type;//在专门化中不存在
};
模板
结构移动\u如果可能\u分配器
:std::分配器{
类型定义移动特征;
//如果有专门化,SFINAE将选择此函数
void构造(typename traits::may_move_type*obj、T和value){
新建(obj)T();//默认构造
traits::move_obj(*obj,value);//自定义例程
}
//如果traits是基本模板,SFINAE将选择此函数
void构造(typename traits::must_copy_type*obj、T const和value){
新建(obj)T(值);//复制构造(回退情况)
}
//为读者定义重新绑定…练习;v)
};
模板
结构移动特征{
typedef T may_move_type;//表示存在专门化
静态无效移动对象(BlitSurface&out、BlitSurface&in){
//填写并清除
}
}

当然,如果某些对象实际上被复制到容器中,那么向BlitSurface添加状态以禁用通过
move\u obj
移动是完全可以的。

定义了一个标准的
insert\u迭代器
适配器来调用某个容器的
insert
,该适配器反过来又被定义为使用复制构造函数--IOW,
insert\u iterate或者
必须按照标准使用复制ctor。因此,您需要定义一个不同的适配器,以减少复制量(但是,如果您确实希望使用底层容器的
插入
方法,您可能仍然需要复制至少一个新构建的默认项!)@Alex-我有个主意,但我不知道怎么做。我可以创建一个默认对象(_surface=NULL)。然后将其添加到容器中。在这种情况下,复制构造函数只需将_surface设置为NULL。然后,在事实发生后,我可以在容器中设置对象的成员。但是,同样,我无法将其用于插入迭代器。您知道如何做吗?@user,插入迭代器的标准实现adapter在
operator=
中增加插入指针,因此,同样,您不能使用特定的适配器:您需要实现自己的专用迭代器适配器。您的代码对我来说是希腊语,但我理解您的解释。到目前为止,我一直避免使用分配器,我想是时候了解它们了。我现在无法有效地实现这一点,但你为我指明了正确的方向。谢谢。
    BlitSurface bs;
    bs._surface = temp_surf[i];
    *it = bs;
    BlitSurface* bs = new BlitSurface;
    bs->_surface = temp_surf[i];
    *it = bs;
template< typename T >
struct move_traits {
    typedef T must_copy_type; // does not exist in specializations
};

template< typename T >
struct move_if_possible_allocator
    : std::allocator< T > {
    typedef move_traits<T> traits;

        // SFINAE selects this function if there is a specialization
    void construct( typename traits::may_move_type *obj, T &value ) {
        new( obj ) T(); // default construct
        traits::move_obj( *obj, value ); // custom routine
    }

        // SFINAE selects this function if traits is the base template
    void construct( typename traits::must_copy_type *obj, T const &value ) {
        new( obj ) T( value ); // copy construct (fallback case)
    }

    // define rebind... exercise for the reader ;v)
};

template<>
struct move_traits< BlitSurface > {
    typedef T may_move_type; // signal existence of specialization
    static void move_obj( BlitSurface &out, BlitSurface &in ) {
        // fill out and clear in
    }
}