如何定义从虚拟继承的静态函数?

时间:2017-02-14 23:25:52

标签: c++ inheritance static virtual-functions

我正在使用C ++进行一些小应用程序。 我有一个具有虚方法的父类。这是头文件。

class personDB:public person
{
public:
    unsigned int id;
public:
    personDB();
    personDB(QString dbName, QString dbSurname);
    personDB(QString dbName, QString dbSurname, unsigned int dbid);
    personDB(std::string dbName, std::string dbSurname, unsigned int dbid);
    virtual std::string getTableName();
    unsigned int getID(void);
    void setID(unsigned int myID);
private:
    static const std::string tableName;
};

此类由不同的子类继承。每个子类重新定义{。{1}}属性,在* .cpp文件中分配不同的值。该属性是私有的,由getter返回。 作为其中一个子类的示例,这里是头文件:

tableName

我想让函数getTableName()成为一个类成员函数,以便它为同一个类的所有实例返回相同的值,即使没有该类的实例也可以调用它。这应该通过在头文件中的函数声明之前放置关键字#include "persondb.h" class ScriptBy : public personDB { public: ScriptBy(); ScriptBy(QString dbName, QString dbSurname); ScriptBy(QString dbName, QString dbSurname, unsigned int dbid); std::string getTableName(); protected: static const std::string tableName; }; 来完成,如果我没有错的话。但是当我尝试以这种方式编译时,它给了我一个与父类中的函数被声明为虚拟的事实相关的错误。 我得到的错误是:

static

有没有办法让继承的类成员函数变为静态?

编辑:如果我不能使该函数成为静态的,那么如何在没有该类的实例的情况下使私有属性可访问(并将其保持为私有)?

4 个答案:

答案 0 :(得分:2)

  

有没有办法让继承的类成员函数变为静态?

你做不到。您可以将static函数重命名为其他函数,并在常规成员函数中使用它,如果这对您的类有意义的话。

class ScriptBy : public personDB
{
    virtual std::string getTableName() { return getTableNameStatic(); }
    static std::string getTableNameStatic();
};

答案 1 :(得分:1)

virtualstatic代表两个相互矛盾的要求。

static函数是类级构造,不受任何特定类实例的约束。

virtual函数是实例级结构,因此它的行为由相关对象定义。

您需要重新考虑您的要求。

答案 2 :(得分:0)

我找到了使用Curiously Recurring template pattern的解决方案。

对我有用的解决方案如下:

文件persondb.h

#ifndef PERSONDB_H
#define PERSONDB_H

#include "person.h"
#include"common.h"
class personDB:public person
{
public:
    using person::person;
    personDB(QString dbName, QString dbSurname, unsigned int dbid);
    personDB(std::string dbName, std::string dbSurname, unsigned int dbid);
    unsigned int getID(void);
    void setID(unsigned int myID);
protected:
    unsigned int id;
};

/* Curiously recurring template paradigm */
template<class Derived>
class PersonDBX: public virtual personDB
{
    using personDB::personDB;
protected:
    static const std::string tableName;
    static const personRelationTable personIDtable;
public:
    static std::string static_getTableName(){ return tableName; }
    std::string getTableName(){return tableName;}
    static std::string static_getIDTableName(){ return personIDtable.tableName; }
    std::string getIDTableName(){return personIDtable.tableName;}

    static std::string static_getCol1TableID(){ return personIDtable.col1; }
    std::string getCol1TableID(){return personIDtable.col1;}

    static std::string static_getCol2TableID(){ return personIDtable.col2; }
    std::string getCol2TableID(){return personIDtable.col2;}



    personDBX(QString dbName, QString dbSurname, unsigned int dbid):personDB(dbName, dbSurname)
    {
        id = dbid;
    }
    PersonDBX():personDB(){;}

    PersonDBX(QString dbName, QString dbSurname):personDB(dbName, dbSurname){;}
};
template<class Derived> const std::string PersonDBX<Derived>::tableName = "Null";
template<class Derived> const personRelationTable PersonDBX<Derived>::personIDtable = {"Null", "Null", "Null"};

#endif // PERSONDB_H

文件persondb.cpp

#include "persondb.h"

personDB::personDB(QString dbName, QString dbSurname, unsigned int dbid):person(dbName, dbSurname){

    id = dbid;
}

personDB::personDB(std::string dbName, std::string dbSurname,
                   unsigned int dbid):person(dbName, dbSurname){

    id = dbid;
}

unsigned int personDB::getID(void){
    return id;
}

void personDB::setID(unsigned int myID)
{
    id = myID;
}

子类是scriptby:

file scriptby.h

#ifndef SCRIPT_H
#define SCRIPT_H

#include "persondb.h"

class ScriptBy : public PersonDBX<ScriptBy>
{
public:
    using PersonDBX::PersonDBX;
    ScriptBy(QString dbName, QString dbSurname, unsigned int dbid);
protected:
};

#endif // SCRIPT_H

file scriptby.cpp

#include "scriptby.h"
#include <iostream>
#include <globals.h>

template<> const std::string PersonDBX<ScriptBy>::tableName = "ScriptBy";
template<> const personRelationTable PersonDBX<ScriptBy>::personIDtable = {"Story_ScriptBy","StoryID", "ScriptByID"};

ScriptBy::ScriptBy(QString dbName, QString dbSurname, unsigned int dbid):PersonDBX(dbName, dbSurname)
{
    id = dbid;
}

答案 3 :(得分:-2)

&#34;有没有办法让继承的类成员函数变为静态?&#34;