"""Object-Oriented Programming: Twitter example === CSC148 Winter 2021 === Department of Mathematical and Computational Sciences, University of Toronto Mississauga === Module description === This module contains two sample classes Tweet and Person that we developed as a way to introduce the major concepts of object-oriented programming. """ from __future__ import annotations # Reference: 1.4 Type Annotations from datetime import date # Python library for working with dates (and times) from typing import List # Python library for expressing complex types class Tweet: """A tweet, like in Twitter. === Attributes === content: the contents of the tweet. userid: the id of the user who wrote the tweet. created_at: the date the tweet was written. likes: the number of likes this tweet has received. === Representation Invariants === - len(self.content) <= 280 Question for next class: how do we enforce this invariant? """ # Attribute types content: str userid: str created_at: date likes: int def __init__(self, who: str, when: date, what: str) -> None: """Initialize a new Tweet. >>> t = Tweet('Rukhsana', date(2017, 9, 16), 'Hey!') >>> t.userid 'Rukhsana' >>> t.created_at datetime.date(2017, 9, 16) >>> t.content 'Hey!' >>> t.likes 0 """ self.userid = who self.content = what self.created_at = when self.likes = 0 def like(self, n: int) -> None: """Record the fact that this tweet received likes. These likes are in addition to the ones already has. >>> t = Tweet('Rukhsana', date(2017, 9, 16), 'Hey!') >>> t.like(3) >>> t.likes 3 """ self.likes += n def edit(self, new_content: str) -> None: """Replace the contents of this tweet with the new message. >>> t = Tweet('Rukhsana', date(2017, 9, 16), 'Hey!') >>> t.edit('Rukhsana is cool') >>> t.content 'Rukhsana is cool' """ # Note: this is the incorrect version from the worksheet. # Notice how both PyCharm and python_ta pick up on this error. old_user = self.userid old_date = self.created_at self = Tweet(old_user, old_date, new_content) class User: """A Twitter user. === Attributes === userid: the userid of this Twitter user. bio: the bio of this Twitter user. tweets: a list of the tweets that this user has made. follows: a list of users that this user follows """ userid: str bio: str tweets: List[Tweet] follows: List[User] def __init__(self, id_: str, bio: str) -> None: """Initialize this User. >>> david = User('David', 'is cool') >>> david.tweets [] """ # Remember to initialize attributes... self.userid = id_ self.bio = bio self.tweets = [] self.follows = [] # Don't forget about this! def tweet(self, message: str) -> None: """Record that this User made a tweet with the given content. Use date.today() to get the current date for the newly created tweet. """ new_tweet = Tweet(self.userid, date.today(), message) self.tweets.append(new_tweet) def follow_user(self, other_user: User) -> None: """Record that this user follows the other user. Just one of many possible implementations. Other possibilities include: - storing userid (a string) rather than the User - using an additional attribute to store num_followed - using an additional list to store followers as well """ self.follows.append(other_user) if __name__ == '__main__': import python_ta python_ta.check_all(config={ 'extra-imports': ['datetime'] })