从类方法返回一个新实例

发布于 01-17 04:08 字数 3979 浏览 1 评论 0原文

我实现了一个日期类,它计算第二天的日期和前一天的日期。 例如。如果今天是 3/26/2022 (MM/DD/YYYY) 那么我的方法 nextday 给出 3/27/2022。 但是,我没有返回字符串,而是尝试返回一个实例,但它无法正常工作。它正确计算日期,但更改了原始实例。 这是我的课程:

class Date:
    """
    Assigning class arguments
    """
    min_year = 1800
    dow_jan1 = "Wednesday"
    def __init__(self,month=1,day=1,year=min_year):
        """
        Assigning instance arguments and checking the validity of dates.
        If Not valid then an Exception is raised.
        """
        self.c_month = month
        self.c_day = day
        self.c_year = year
        
        if self.c_year < self.min_year:
            raise Exception("Invalid Year")
        elif self.c_month <1 or self.c_month > 12:
            raise Exception("Invalid Month")
        elif self.c_day<1 or self.c_day > 31:
            raise Exception("Invalid Day")
        else:
            if self.c_month == 2:
                if self.year_is_leap(self.c_year):
                    if self.c_day<1 or self.c_day > 29:
                        raise Exception("Invalid Day")
                else:
                    if self.c_day<1 or self.c_day > 28:
                        raise Exception("Invalid Day")
            else:
                months_31_days = [1,3,5,7,8,10,12]
                if self.c_month in months_31_days:
                    if self.c_day<1 or self.c_day > 31:
                        raise Exception("Invalid Day")
                else:
                    if self.c_day<1 or self.c_day > 30:
                        raise Exception("Invalid Day")


    def year_is_leap(self,year=None):
        """
        Finds if a year is Leap or not
        Parameters:
            year : takes a year which is to be checked
                    however if a year is not provided then the instance argument year (self.c_year)
                    is set as default value
        """
        if year is None:
            year = self.c_year
            
        if (year % 4) == 0:
            if (year % 100) == 0:
                if (year % 400) == 0:
                    return True
                else:
                    return False
            else:
                 return True
        else:
            return False

    
    def __str__(self):
        """
        returns the date in suitable format
        eg. 2/14/1900 => February 14, 1900
        """
        months = {1:"January",2:"February",3:"March",4:"April",
                  5:"May",6:"June",7:"July",8:"August",9:"September",
                  10:"October",11:"November",12:"December"}
        return "{} {}, {}".format(months[self.c_month],self.c_day,self.c_year)
        

    def nextday(self):
        """
        Returns next date in date object
        """
        leap_year = self.year_is_leap(self.c_year)
        #print(leap_year)

        if self.c_month in (1, 3, 5, 7, 8, 10, 12):
            month_length = 31
        elif self.c_month == 2:
            if leap_year:
                month_length = 29
            else:
                month_length = 28
        else:
            month_length = 30


        if self.c_day < month_length:
            self.c_day += 1
        else:
            self.c_day = 1
            if self.c_month == 12:
                self.c_month = 1
                self.c_year += 1
            else:
                self.c_month += 1
        print("The next date is [mm-dd-yyyy] %d-%d-%d." % (self.c_month, self.c_day,self.c_year))
        return self #Date(self.c_month,self.c_day,self.c_year) #Date #self.__class__()

    ```

I've tried to return `self`, `Date()`, `Date(self.c_month,self.c_day,self.c_year)` and `self.__class__()`, however none of it worked.
When I run:

firstdate = Date(1,1,Date.min_year) 打印(第一次日期) print("之后的日期",firstdate,"is",firstdate.nextday())


I am getting the output:

1800 年 1 月 1 日 下一个日期是 [mm-dd-yyyy] 1-2-1800。 1800年1月2日之后的日期是1800年1月2日

I've implemented a date class, which calculates the next day's date and the previous day's date.
eg. if today is 3/26/2022 (MM/DD/YYYY) then my method nextday gives 3/27/2022.
However, instead of returning a string, I am trying to return an instance but it's not working properly. It's calculating the day correctly but changes the original instance.
This is my class:

class Date:
    """
    Assigning class arguments
    """
    min_year = 1800
    dow_jan1 = "Wednesday"
    def __init__(self,month=1,day=1,year=min_year):
        """
        Assigning instance arguments and checking the validity of dates.
        If Not valid then an Exception is raised.
        """
        self.c_month = month
        self.c_day = day
        self.c_year = year
        
        if self.c_year < self.min_year:
            raise Exception("Invalid Year")
        elif self.c_month <1 or self.c_month > 12:
            raise Exception("Invalid Month")
        elif self.c_day<1 or self.c_day > 31:
            raise Exception("Invalid Day")
        else:
            if self.c_month == 2:
                if self.year_is_leap(self.c_year):
                    if self.c_day<1 or self.c_day > 29:
                        raise Exception("Invalid Day")
                else:
                    if self.c_day<1 or self.c_day > 28:
                        raise Exception("Invalid Day")
            else:
                months_31_days = [1,3,5,7,8,10,12]
                if self.c_month in months_31_days:
                    if self.c_day<1 or self.c_day > 31:
                        raise Exception("Invalid Day")
                else:
                    if self.c_day<1 or self.c_day > 30:
                        raise Exception("Invalid Day")


    def year_is_leap(self,year=None):
        """
        Finds if a year is Leap or not
        Parameters:
            year : takes a year which is to be checked
                    however if a year is not provided then the instance argument year (self.c_year)
                    is set as default value
        """
        if year is None:
            year = self.c_year
            
        if (year % 4) == 0:
            if (year % 100) == 0:
                if (year % 400) == 0:
                    return True
                else:
                    return False
            else:
                 return True
        else:
            return False

    
    def __str__(self):
        """
        returns the date in suitable format
        eg. 2/14/1900 => February 14, 1900
        """
        months = {1:"January",2:"February",3:"March",4:"April",
                  5:"May",6:"June",7:"July",8:"August",9:"September",
                  10:"October",11:"November",12:"December"}
        return "{} {}, {}".format(months[self.c_month],self.c_day,self.c_year)
        

    def nextday(self):
        """
        Returns next date in date object
        """
        leap_year = self.year_is_leap(self.c_year)
        #print(leap_year)

        if self.c_month in (1, 3, 5, 7, 8, 10, 12):
            month_length = 31
        elif self.c_month == 2:
            if leap_year:
                month_length = 29
            else:
                month_length = 28
        else:
            month_length = 30


        if self.c_day < month_length:
            self.c_day += 1
        else:
            self.c_day = 1
            if self.c_month == 12:
                self.c_month = 1
                self.c_year += 1
            else:
                self.c_month += 1
        print("The next date is [mm-dd-yyyy] %d-%d-%d." % (self.c_month, self.c_day,self.c_year))
        return self #Date(self.c_month,self.c_day,self.c_year) #Date #self.__class__()

    ```

I've tried to return `self`, `Date()`, `Date(self.c_month,self.c_day,self.c_year)` and `self.__class__()`, however none of it worked.
When I run:

firstdate = Date(1,1,Date.min_year)
print(firstdate)
print("The date after ", firstdate, "is", firstdate.nextday())


I am getting the output:

January 1, 1800
The next date is [mm-dd-yyyy] 1-2-1800.
The date after January 2, 1800 is January 2, 1800

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

无可置疑2025-01-24 04:08:46

最直接的解决方案是创建一个新的 Date 实例,其值与 self 相同(基本上是复制它)并使用它,而不是更改 self >:

class Date:
    # other methods here

    def nextday(self):
        """
        Returns next date in date object
        """
        new_date = Date(self.c_month, self.c_day, self.c_year)
        is_leap_year = new_date.year_is_leap(new_date.c_year)

        if new_date.c_month in {1, 3, 5, 7, 8, 10, 12}:
            month_length = 31
        elif new_date.c_month == 2:
            month_length = 28 + is_leap_year
        else:
            month_length = 30


        if new_date.c_day < month_length:
            new_date.c_day += 1
        else:
            new_date.c_day = 1
            if new_date.c_month == 12:
                new_date.c_month = 1
                new_date.c_year += 1
            else:
                new_date.c_month += 1
        print("The next date is [mm-dd-yyyy] %d-%d-%d." % (new_date.c_month, new_date.c_day,new_date.c_year))
        return new_date

您还可以实现一些方便的方法(例如 .copy 复制日期或 __format__ 打印日期,但这超出了问题范围)

The most straightforward solution will be creating a new instance of Date with same values as self (basically copy it) and work with it, not changing self:

class Date:
    # other methods here

    def nextday(self):
        """
        Returns next date in date object
        """
        new_date = Date(self.c_month, self.c_day, self.c_year)
        is_leap_year = new_date.year_is_leap(new_date.c_year)

        if new_date.c_month in {1, 3, 5, 7, 8, 10, 12}:
            month_length = 31
        elif new_date.c_month == 2:
            month_length = 28 + is_leap_year
        else:
            month_length = 30


        if new_date.c_day < month_length:
            new_date.c_day += 1
        else:
            new_date.c_day = 1
            if new_date.c_month == 12:
                new_date.c_month = 1
                new_date.c_year += 1
            else:
                new_date.c_month += 1
        print("The next date is [mm-dd-yyyy] %d-%d-%d." % (new_date.c_month, new_date.c_day,new_date.c_year))
        return new_date

You could also implement some convenience methods (e.g. .copy to copy the date or __format__ to print the date, but that's out of question scope)

忱杏2025-01-24 04:08:46

问题是您更改了对象属性。例如,在 nextday 方法中,您编写 self.c_day += 1,您正在更改对象本身。
相反,如果您想返回新的日期,则需要编写 c_day += 1 然后返回 Date(c_month, c_day, c_year)

The problem is that you change the object attributes. For example on nextday method, you write self.c_day += 1, you are changing the object itself.
Instead, if you want to return a new Date, you need to write c_day += 1 then return Date(c_month, c_day, c_year)

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文