2

我主要有以下内容:

Sum *sum = new Sum(Identifier("aNum1"), Identifier("aNum2"));

我的课程是:

class Table {
private:
    static map<string, int> m;    
public:
    static int lookup(string ident)
    {
        return m.find(ident)->second;
    }
    static void insert(string ident, int aValue)
    {
        m.insert(pair<string, int>(ident, aValue));
    }
};   

class Expression {
public:
    virtual int const getValue() = 0;
};

class Identifier : Expression {
private:
    string ident;
public:
    Identifier(string _ident) { ident = _ident; }
    int const getValue() { return Table::lookup(ident); }    
};

class BinaryExpression : public Expression {
protected:
    Expression *firstExp;
    Expression *secondExp;
public:
    BinaryExpression(Expression &_firstExp, Expression &_secondExp) {
        firstExp = &_firstExp;
        secondExp = &_secondExp;
    }
};

class Sum : BinaryExpression {
public:
    Sum(Expression &first, Expression &second) : BinaryExpression (first, second) {}
    int const getValue() 
    { 
        return firstExp->getValue() + secondExp->getValue();
    }
};

当我编译它时,我收到以下错误:

调用 'Sum::Sum(Identifier, Identifier)' 没有匹配的函数

候选人是: Sum::Sum(Expression&, Expression&)

Identifier 类继承自 Expression,那么为什么会出现此错误?

4

5 回答 5

7

问题是您将临时对象传递给构造函数,但构造函数需要引用,const而临时对象只能绑定到const引用。

要修复它,请将参数类型更改为Expression const&. 顺便说一句,这与继承和多态性完全无关(但也需要 digivampire 的修复;我怀疑这只是一个错字)。

于 2011-11-02T13:04:40.267 回答
4
class Identifier : Expression {
private:
    string ident;
public:
    Identifier(string _ident) { ident = _ident; }
    int const getValue() { return Table::lookup(ident); }    
};

您正在从 Expression 私下继承 Identifier 更改为:

class Identifier : public Expression {
private:
    string ident;
public:
    Identifier(string _ident) { ident = _ident; }
    int const getValue() { return Table::lookup(ident); }    
};
于 2011-11-02T12:57:26.503 回答
0

你需要Sum(Expression const & first, Expression const & second).

没有consts 它不会编译 - 非常量引用不会绑定到临时对象,比如你的临时Identifier对象。

但即使那样它也行不通——你最终会得到指向标识符的悬空指针。你可能会更好地使用类似的东西:

new Sum(new Identifier("aNum1"), new Identifier("aNum2"));

但是你需要弄清楚如何在正确的时间释放东西。

于 2011-11-02T13:06:49.473 回答
-1

据我了解,向下转换(这是你想要实现的)不是自动的,你应该强制它。

但是,要将 Identifier 转换为 Expression,您需要指向这些对象的指针。因此,如果你想保持 Sum 类构造函数的原样,你需要这样调用它:

Identifier a("aNum1");
Identifier b("aNum2");
Sum *sum = new Sum(*(Expression*) &a, *(Expression*) &b);
于 2011-11-02T13:54:51.233 回答
-3

继承无关紧要。您应该传递 Expression 而不是 Identifier 的实例。

Sum *sum = new Sum(Expression("aNum1"), Expression("aNum2"));
于 2011-11-02T12:58:27.737 回答