为什么'const'在这两种情况下表现不同?

问题描述 投票:0回答:3

我有一个问题,为什么为什么要“一步一步”编译某个东西,而不能“一步一步”编译却不能编译。我有三节课;

class Time {
  int mTime;

  int Time::getTimeAsUnix() const {return mTime;}
}

class Travel {
  Time mTimestamp;

  const Time& Travel::getTime() const { return mTimestamp; }
  Time& Travel::getTime() { return mTimestamp; }
}

class Analysis : public Travel {

  int Analysis::getUnixTime() const {
    // Time& t = Travel::getTime();
    // return t.getTimeAsUnix();     // This does NOT compile

    return Travel::getTime().getTimeAsUnix();  // This compiles
  }
}

[任何人都知道为什么在Analysis类中会编译非注释方法,而注释方法会立即给我“ c ++错误:将'const Time'绑定到类型'Time&'的引用会丢弃限定符”试试吗?

执行时两个不是完全相同的东西吗?

c++ reference const qualifiers
3个回答
3
投票

Time& t = Travel::getTime();

需要成为

const Time& t = Travel::getTime();

使其正常工作。之所以需要这样做,是因为您在const限定的函数内。当您使用const限定的函数时,该类的所有成员均被视为const。这意味着当您呼叫getTime时,您会呼叫

const Time& Travel::getTime() const { return mTimestamp; }

功能版本。尝试将const Time&分配给Time&无效,因为您将剥离返回类型的常量。


3
投票

在此函数定义中,应删除Analysis::

  int Analysis::getUnixTime() const {
     Time& t = Travel::getTime();
     return t.getTimeAsUnix();  
  }

被称为函数

const Time& Travel::getTime() const { return mTimestamp; }

返回常量引用。使用此重载函数是因为函数getUnixTime声明为const成员函数。

但是常量引用分配给非常量引用

     Time& t = Travel::getTime();

所以编译器会发出错误。


0
投票

好,让我们分解工作版本:

int Analysis::getUnixTime() const { // (1)
    // (2) --------v        v----- (3)
    return Travel::getTime().getTimeAsUnix();
}

(1),函数getUnixTime被定义为在常量实例上工作。这意味着您只能调用其他常量函数,而不能更改任何成员变量。

(2)处,调用Travel::getTime()。尽管调用它的语法,该调用非静态成员函数。但这没关系,很明显,并调用了函数的const版本,该函数返回const Time&。对常量Time对象的引用。

(3),成员函数getTimeAsUnixconst Time&上被调用。这是完美的,因为Time的成员函数被命名为可以在常量对象上工作的方式。

因此,您看到的每个对象都是常量,您只调用常量函数。


当您在两行中分解代码时出了什么问题?

让我们看一下函数正文的第一行:

Time& t = Travel::getTime();

如上所述,Travel::getTime()调用非静态成员函数。由于this是一个常量对象(您在const函数中),因此getTime的const版本会像以前一样被调用。

const getTime的返回类型为const Time&

然后您进行Time& t =。这是您的错误所在。 const Time&无法修改。可以修改Time&。如果您使用可变引用来引用常量对象,则可以使常量对象发生突变。语言禁止这样做!

要解决此问题,只需使用常量引用:

const Time& t = Travel::getTime();
© www.soinside.com 2019 - 2024. All rights reserved.