Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/templates/2.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++ 使用模板时如何从std::vector中删除元素?_C++_Templates_Vector - Fatal编程技术网

C++ 使用模板时如何从std::vector中删除元素?

C++ 使用模板时如何从std::vector中删除元素?,c++,templates,vector,C++,Templates,Vector,我有一个非常简单的模板类,其中我将项目存储在向量中。但是,当我尝试擦除某个元素时,会出现以下错误: C2678: binary '==': no operator found which takes a left-hand operand of type 'TestComponent' (or there is no acceptable conversion) 以下是我使用的代码: #pragma once #include <vector> template<

我有一个非常简单的模板类,其中我将项目存储在向量中。但是,当我尝试擦除某个元素时,会出现以下错误:

C2678: binary '==': no operator found which takes a left-hand operand of type
      'TestComponent' (or there is no acceptable conversion)
以下是我使用的代码:

#pragma once
#include <vector>

template<class T>
class ComponentManager {
    ComponentManager() {};
    ~ComponentManager() {};

    T* newComponent() {
        components.emplace_back(T());
        return &components.back();
    }

    // This is the method I'm having trouble with
    void destroyComponent(T* t) {
        components.erase(std::remove(components.begin(), components.end(), *t), components.end());
    }

private:
    std::vector<T> components;
};
#pragma一次
#包括
模板
类组件管理器{
ComponentManager(){};
~ComponentManager(){};
T*newComponent(){
组件。向后放置(T());
返回&components.back();
}
//这是我遇到麻烦的方法
空心构件(T*T){
擦除(std::remove(components.begin()、components.end()、*t)、components.end());
}
私人:
std::向量分量;
};


是的,我知道这会导致指针失效等等。无需执行此操作。

std::remove
在给定序列中搜索指定为第三个参数的给定值,该序列由起始迭代器和结束迭代器定义。显然,值的类型必须实现相等比较运算符,以便
std::remove
将序列中的值与给定值进行比较


您的
TestComponent
类没有实现
=
操作符,正如错误消息所说。

std::remove
搜索给定序列(由开始迭代器和结束迭代器定义),以获得指定为第三个参数的给定值。显然,值的类型必须实现相等比较运算符,以便
std::remove
将序列中的值与给定值进行比较

您的
TestComponent
类没有实现
=
操作符,正如错误消息所说。

如果您试图通过指针擦除,则需要使用正确的算法<代码>标准::删除在元素之间进行相等比较。根据您的意见,您不想要求这样做,因此您可能更喜欢:


请注意,保留
向量中的指针并不特别安全,因为插入向量可能导致重新分配,这将使以前保留的所有指针无效。你可能想考虑一个不同的容器(或者只是有一个<代码>向量<代码>,或者更好的是,<代码>向量< /代码>。

如果你试图用指针擦除,你需要使用正确的算法。代码>标准::删除
在元素之间进行相等比较。根据您的意见,您不想要求这样做,因此您可能更喜欢:



请注意,保留
向量中的指针并不特别安全,因为插入向量可能导致重新分配,这将使以前保留的所有指针无效。你可能想考虑一个不同的容器(或者只是有一个<代码>向量<代码>,或者更好,<代码>向量< /代码>.

首先,您的解决方案是危险的:看起来您保留了存储在
std::vector
中的对象指针,除非您提前预留足够的空间,否则在添加新元素时,您将得到一个悬空的指针。如果您预留了足够的空间,您可能应该按指针而不是按值删除对象:

components.erase(std::remove_if(components.begin(), components.end(), [t]( const T &tc ) { return &tc == t; } ), components.end());
除非您可以通过值唯一地标识对象,然后需要为该类实现适当的
操作符==

我建议使用
std::unique\u ptr
存储
TestComponent
,这样您就不会出现通过
std::vector
重新分配内存的问题,并且您的删除操作将按预期进行,而无需实现
运算符==

template<class T>
class ComponentManager {
    ComponentManager() {};
    ~ComponentManager() {};

     template< class... Args >
     T *newComponent( Args...&& args ) {
        components.emplace_back(std::make_unique<T>(std::forward<Args>(args)...));
        return components.back().get();
    }

    // This is the method I'm having trouble with
    void destroyComponent(T* t) {
        components.erase(std::remove(components.begin(), components.end(), t), components.end());
    }

private:
    std::vector<std::unique_ptr<T>>> components;
};
模板
类组件管理器{
ComponentManager(){};
~ComponentManager(){};
模板<类…参数>
T*newComponent(参数…&&Args){
组件。向后放置(std::使_唯一(std::向前(args)…);
返回组件.back().get();
}
//这是我遇到麻烦的方法
空心构件(T*T){
擦除(std::remove(components.begin()、components.end()、t)、components.end());
}
私人:
std::vector>分量;
};

首先,您的解决方案是危险的:看起来您保留了存储在
std::vector
中的对象指针,除非您提前预留足够的空间,否则在添加新元素时,您将得到一个悬空的指针。如果您预留了足够的空间,您可能应该按指针而不是按值删除对象:

components.erase(std::remove_if(components.begin(), components.end(), [t]( const T &tc ) { return &tc == t; } ), components.end());
除非您可以通过值唯一地标识对象,然后需要为该类实现适当的
操作符==

我建议使用
std::unique\u ptr
存储
TestComponent
,这样您就不会出现通过
std::vector
重新分配内存的问题,并且您的删除操作将按预期进行,而无需实现
运算符==

template<class T>
class ComponentManager {
    ComponentManager() {};
    ~ComponentManager() {};

     template< class... Args >
     T *newComponent( Args...&& args ) {
        components.emplace_back(std::make_unique<T>(std::forward<Args>(args)...));
        return components.back().get();
    }

    // This is the method I'm having trouble with
    void destroyComponent(T* t) {
        components.erase(std::remove(components.begin(), components.end(), t), components.end());
    }

private:
    std::vector<std::unique_ptr<T>>> components;
};
模板
类组件管理器{
ComponentManager(){};
~ComponentManager(){};
模板<类…参数>
T*newComponent(参数…&&Args){
组件。向后放置(std::使_唯一(std::向前(args)…);
返回组件.back().get();
}
//这是我遇到麻烦的方法
空心构件(T*T){
擦除(std::remove(components.begin()、components.end()、t)、components.end());
}
私人:
std::vector>分量;
};

是否定义了
TestComponent
运算符==
。我想尽量不需要它,因为泛型类型可以是任何类型。我可能只是制定了错误的删除方法。与手头的问题无关,你不必写
emplace\u back(t())
,你只需写
emplace\u back()
@manabreak就可以删除你需要检查它们是否相等的东西。如果要提供比较两个对象的方法,则需要使用
remove\u。为什么要使用原始指针而不是引用