【问题标题】:My Time program does not overload. Why?我的时间程序不会超载。为什么?
【发布时间】:2018-03-26 20:47:27
【问题描述】:

我制作了一个程序,它可以记录时间并显示它们。在某些情况下,用户可能会超载时间。当我随时间重载构造函数时,它不会正确重载,而且如果重载,(AM/PM)也会变得不正确。有一些我找不到的逻辑错误。我该如何解决这个问题,我的错误在哪里?我想要的是,如果我要在构造函数中投入 25 个小时,它会滚动到凌晨 1 点。

/**  Time.h**/
#ifndef TIME_H_
#define TIME_H_

#include <iostream>
#include <string>
/***  Time class**  The Time class contains time as   hours:minutes:seconds:milliseconds (AM/PM).*/

class Time {
    public:
    /** *  Constructor with zero values */
    Time();

    /** *  Constructors with arguments */
    Time(long long time);
    Time(int hours, int minutes, int seconds, int milli);

    /** *  Deconstructor */
    virtual ~Time();

    /** *  Return time as   a  long long value representing time in milliseconds */
    long long asLong() const;

    /** *  Provide a  string in the format hours:minutes:seconds:milliseconds. *  For example 1:45:30:56 PM */
    std::string toString() const;

    /** *  Output the time to   an   output stream as hours:minutes:seconds:milliseconds AM/PM */
    friend std::ostream& operator <<(std::ostream&, const Time&);

    // Output a Time to an output stream

/** *  Declare ordering relationships */
    friend bool operator <(const Time&, const Time&);
    friend bool operator >(const Time&, const Time&);
    friend bool operator ==(const Time &a, const Time &b);

    /** *  Declare addition and subtraction */
     friend Time operator +(const Time&, const Time&);
     friend Time operator -(const Time&, const Time&);

private:
int hours;
int minutes;
int seconds;
int millis;
};

#endif /*   TIME_H_ */

以下是源码

#include "Time.h"
#include <sstream>
#include <string>

using namespace std;

// Defualt Constructor
Time::Time() {
    hours = 0;
    minutes = 0;
    seconds = 0;
    millis = 0;
}

// Constructors with arguments

Time::Time(long long timeValue) {
    long long tempValue = timeValue;
    millis = tempValue % 1000;
    tempValue /= 1000;
    seconds = tempValue % 60;
    tempValue /= 60;
    minutes = tempValue % 60;
    tempValue /= 60;
    hours = tempValue;
}

Time::Time(int hours, int minutes, int seconds, int millis) {
    this->hours = hours;
    this ->minutes = minutes;
    this -> seconds = seconds;
    this -> millis = millis;

}

// Destructor
Time::~Time() {

}

// Return time in term of milliseconds.

long long Time::asLong() const {
    long long timeValue = (long long) hours;
    timeValue = (timeValue * 60) + minutes;
    timeValue = (timeValue * 60) + seconds;
    timeValue = (timeValue * 1000) + millis;
    return timeValue;
}

// Formatting

std::string Time::toString() const {
    ostringstream  v1;
    string ph;

    if (hours <= 12)
        ph = "am";
    else
        ph = "pm";

    v1 << hours % 12 << ":" << minutes << ":" << seconds << ":" << millis << ph;

    return v1.str();
}

// Time to Output Stream
ostream& operator <<(ostream& b, const Time& c)
{
    return b << c.toString();
}

// Ordering Relationships
bool operator <(const Time&t1, const Time&t2)
{
    return t1.asLong() < t2.asLong();
}

bool operator >(const Time&t1, const Time&t2)
{
    return t1.asLong() > t2.asLong();
}
bool operator ==(const Time &a, const Time &b)
{
    return a.asLong() == b.asLong();
}

// Declare addition and Subtraction
Time operator +(const Time&t1, const Time&t2)
{
    int a,b,c,d;
    a = t1.hours+t2.hours;
    b = t1.minutes+t2.minutes;
    c = t1.seconds+t2.seconds;
    d = t1.millis+t2.millis;
    if (d > 999)
    {
        c = c+1;
        d = d - 1000;
    }
    if (c > 59)
    {
        b = b + 1;
        c = c - 60;
    }
    if (b > 59)
    {
        a = a+1;
        b = b-60;
    }
    if (a > 24)
    {
        a = a - 24;
    }
    return Time(a,b,c,d);
}
Time operator -(const Time&t1, const Time&t2)
{
    int a,b,c,d;
    a = t1.hours-t2.hours;
    b = t1.minutes-t2.minutes;
    c = t1.seconds-t2.seconds;
    d = t1.millis - t2.millis;
    if (d < 0)
    {
        c = c -1;
        d = d + 1000;
    }
    if (c < 0)
    {
        b = b - 1;
        c = c + 60;
    }
    if (b < 0)
    {
        a = a + 1;
        b = b - 60;
    }
    if (a < 24)
    {
        a = a + 24;
    }

    return Time(a,b,c,d);
}

下面是我插入的内容:

   #include <iostream>
#include "Time.h"
using namespace std;

int main() {
    // Tests for user-defined methods.
        Time zeroTime;
        Time oneTime(1L);
        Time twoTime(4,30,26,72);
        Time threeTime(24,00,00,00); //Overloaded Hour
        Time fourTime(22,60,00,00); // Overloaded Minutes
        Time fiveTime(22,58,60,00);  // Overloaded Seconds
        Time sixTime(17,28,13,61); // Overloaded Millis


        cout << zeroTime.toString() << endl;
        cout << oneTime.toString() << endl;
        cout << twoTime.toString() << endl;
        cout << zeroTime.asLong() << endl;
        cout << oneTime.asLong() << endl;
        cout << twoTime.asLong() << endl;
        cout << threeTime.toString() << endl;
        cout << fourTime.toString() << endl;
        cout << fiveTime.toString() << endl;
        cout << sixTime.toString() << endl;

        return 0;
}

输出如下所示:

0:0:0:0am
0:0:0:1am
4:30:26:72am
0
1
16226072
0:0:0:0pm
10:60:0:0pm
10:58:60:0pm
5:28:13:61pm

如您所见,输出毫无意义。如果我将 60 分钟添加到分钟,那么它应该翻转。这不会发生。

【问题讨论】:

  • 我想你们可能想知道当我不超载时这意味着什么。这就是我的意思。这是程序运行时发生的情况: 0:0:0:0am 0:0:0:1am 4:30:26:72am 0 1 16226072 0:0:0:0pm 10:60:0:0pm 10:58 :60:0pm 5:28:13:61pm
  • 请在您的问题中发表评论。还要说明您期望的输出。
  • 我把输出放在我的问题中。我期待一个合理的输出。如果我在 Time 构造函数中输入 (4,65,13,​​12),那么我希望分钟数会滚动到小时数中,变成 (5,5,13,​​12),因为没有 65 分钟这样的东西一个小时。
  • 我快速查看的三个逻辑错误是 (1) 接受 long long 的构造函数使用模逻辑,因此所有时间都将在 24 小时内拟合,但构造函数它接受单独的小时,分​​钟,....不。 (2) 没有一个操作正确处理负值输入 (3) toString() 方法认为从 0 到 12 小时(所以早上是 13 小时)对应于上午。

标签: c++ class scope logic


【解决方案1】:

C++ 中的Overloading 与函数重载有关,这是一个不同的问题。我认为您的意思是“超小时”之类的。

您正在 long long Time::asLong() 函数中处理此问题。

但打印时不使用该功能。您可以改为修复输入值:

Time::Time(long long timeValue)
{
    setTimeValue(timeValue);
}

Time::Time(int h, int m, int s, int msec)
{
    long long stamp = msec + s * 1000 + m * 1000 * 60 + h * 1000 * 60 * 60;
    setTimeValue(stamp);
}

void Time::setTimeValue(long long timeValue)
{
    long long tempValue = timeValue;
    millis = tempValue % 1000;
    tempValue /= 1000;
    seconds = tempValue % 60;
    tempValue /= 60;
    minutes = tempValue % 60;
    tempValue /= 60;
    hours = (int)tempValue;

    //make sure hours is never >= 24
    //note: an extra day or more could be lost here:
    hours %= 24;
}

更好的方法是同时获取日、月、年。然后用户long long返回值作为时间戳,然后添加/减去日期时间戳。

为了计算 AM/PM,你有:

if (hours <= 12)
    ph = "am";
else
    ph = "pm";

这会导致下午 12:01 出现问题,而不是上午。更改代码,使任何稍微超过 12:00 的时间始终为 PM。我们假设任何 &gt;= 00:00 都是 AM

std::string Time::toString() const 
{
    ostringstream  v1;
    string ph;

    if(hours < 12)
        ph = "am";
    else if (hours == 12 && minutes == 0 && seconds == 0 && millis == 0)
        ph = "am";
    else
        ph = "pm";

    v1 << hours % 12 << ":" << minutes << ":" << seconds << ":" << millis << " " << ph;

    return v1.str();
}

重载运算符的示例是您的方法:

ostream& operator <<(ostream& b, const Time& c)

它可以让您在没有toString 运算符的情况下打印结果。

cout << sixTime << endl;

C++ 函数重载也指函数重载,例如派生类。查看在线资源。

【讨论】:

  • 所以,我尝试了这个,它解决了我的问题,除了 (am/pm) 功能仍然关闭。我的 asLong() 函数中是否还缺少 am/pm 检查器?另外,函数重载是否意味着我实际上在 main 之外定义了一个函数并且在使用时会被重载?谢谢。
  • 另外,我究竟要如何超载milli?我到了这一步。 int add_millis = 毫;分钟 -= add_millis *1000; Millis += add_millis;
  • 我认为我以前的做法令人困惑。最好一次性完成所有计算。请参阅更新的代码。我只是在使用你的旧 Time(int h, int m, int s, int msec) 构造函数,但将它移到了一个新函数 setTimeValue,它被两个构造函数使用。添加了上午/下午的修复
  • 我正在为一个项目执行此操作,我需要使用 toString() 运算符。但无论如何,我输入了修改后的 AM/PM 代码,我得到了同样的错误。我目前的主要错误是那个并且环绕着毫。你说的第一件事很好。
  • 我的上午/下午逻辑错误,请参阅更新后的toString。我没有看到millis的错误。 cout &lt;&lt; Time(0, 0, 0, 1001) 按预期产生 0:0:1:1 am
猜你喜欢
  • 2021-09-30
  • 2019-09-13
  • 1970-01-01
  • 2011-02-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-05-14
  • 1970-01-01
相关资源
最近更新 更多