无法让这个类与模板一起工作?

时间:2015-04-15 20:54:10

标签: c++

我试图在C ++中使用通用对象编写类似C#接口的东西,但我无法使其工作。 每次我在main中创建一个新实例时都会出现以下错误: 错误1错误LNK2019:未解析的外部符号" public:__ thiscall AccountRepository :: AccountRepository(void)"

的main.cpp

#include <iostream>
#include <stdio.h>
#include <string>
#include "AccountRepository.h"

using namespace std;

int main(){

    AccountRepository repo;

    return 0;
}

IRepository.h

#pragma once
#include <vector>
using namespace std;

template <class Entity>
class IRepository
{
public:
    virtual bool add(Entity entity) = 0;
    virtual bool update(Entity entity) = 0;
    virtual Entity getById(int Id) = 0;
    virtual bool remove(Entity entity) = 0;
    virtual vector<Entity> getAll() = 0;
};

AccountRepository.h

#pragma once
#include "IRepository.h"
#include "Account.h"
#include <vector>

class AccountRepository : public IRepository<Account>{
private:
    vector<Account> _accounts;

public:
    AccountRepository();
    ~AccountRepository();

    virtual bool add(Account entity) override;
    virtual bool update(Account entity) override;
    virtual Account getById(int Id) override;
    virtual bool remove(Account entity) override;
    virtual vector<Account> getAll() override;

};

AccountReposity.cpp

#include "AccountRepository.h"

inline AccountRepository::AccountRepository()
{

}

inline AccountRepository::~AccountRepository()
{

}

inline bool AccountRepository::add(Account entity)
{
    _accounts.push_back(entity);
    return true;
}

inline bool AccountRepository::update(Account entity)
{
    for (Account account : _accounts){
        if (account.getId() == entity.getId()){
            account.setName(entity.getName());
            account.setDescription(entity.getDescription());
            return true;
        }
    }

    return false;
}

inline Account AccountRepository::getById(int Id)
{
    for (Account account: _accounts)
    {
        if (account.getId() == Id)
            return account;
    }
}

inline bool AccountRepository::remove(Account entity)
{
    vector<Account>::iterator it;
    for (it = _accounts.begin(); it != _accounts.end(); ++it){
        if (it->getId() == entity.getId())
        {
            _accounts.erase(it);
            return true;
        }
    }

    return false;
}

inline vector<Account> AccountRepository::getAll()
{
    return _accounts;
}

2 个答案:

答案 0 :(得分:2)

您滥用inline关键字。对它进行处理,好像它意味着“此函数的实现位于标题中”。

这会立即显示问题:您的某个cpp文件中有很多inline个函数,这些函数不是标题。使用inline函数的每个cpp文件 required 包含或包含该函数的定义。问题是链接器使用inline函数执行神奇的操作,因为它们应该是许多cpp文件中的每一个的一个副本。因此编译器编译main.cpp,并且(因为main不知道函数是内联的,所以注意稍后链接器应该在默认构造函数中链接)。编译器然后编译AccountReposity.cpp,看到没有使用内联函数,所以只是跳过它。之后,链接器无法找到要使用的AccountRepository()副本,并报告错误。如果正确地在头文件中定义了函数体,那么在编译步骤中,它将在到达链接阶段之前被实例化为main.cpp

某些编译器将inline函数视为特殊的事实并不会真正影响经验法则。其他编译器不会对inline函数进行任何特殊优化,并将其视为优化会导致您遇到的错误。忽略优化会使关键字的位置更加清晰。

答案 1 :(得分:0)

如果要将AccountRepository的成员函数声明为inline,则必须在使用它们的所有翻译单元中使用它们,如[basic.def.odr] / 3所示:

  

(...)内联函数应在每个使用它的翻译单元中定义。

从函数定义中删除inline或将它们全部移到标题中。