首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >会议轨道管理

会议轨道管理
EN

Code Review用户
提问于 2015-03-04 12:56:05
回答 2查看 3.3K关注 0票数 6

我正在学习设计真实世界的OOP问题的方法,我试图用面向对象的方法来解决这个问题。问题陈述如下:

  • 会议有多条轨道,每条轨道都有上午和下午的会议。
  • 每一次会议都包含多个会谈。
  • 上午9点开始上课,中午12点前完成午餐。
  • 下午的会议从下午1点开始,必须及时完成网络活动。
  • 网络事件可以不早于4:00或不晚于5:00开始。
  • 谈话标题里没有数字。
  • 所有的谈话长度要么是分钟(不是小时),要么是闪电(5分钟)。
  • 演讲者将非常准时,会议之间不需要有任何间隙。

在Python45minLua中对企业Rails进行测试输入快速测试--在Python45minLua中,大量使用Gem版本的30分钟Ruby错误,45分钟通用Ruby错误,45 my,Python开发人员闪电通信,60分钟会计驱动的开发45分钟,Woah 30分钟,坐下来写30分钟对程序和噪音45分钟Rails魔术60分钟Ruby on Rails:为什么我们要在西雅图30分钟Boondocks的Boondocks(我的项目中)编写45分钟的Ruby程序,与Ruby开发30分钟Rails应用程序维护60分钟,一个没有HackerNews 30分钟用户界面的世界,在Rails 30分钟测试输出轨道1: 09::00AM编写针对企业Rails的快速测试60分钟10:00AM远程通信60分钟11:00 Rails魔术60分钟12:00 Gem午餐01:00 Gem on Rails:为什么我们应该继续60分钟02:00 Gem常见Ruby错误45min 02:45 Gem公共Ruby错误45min 02:45 Gem会计驱动开发45min 03:30 Gem编程与噪音45min 04:15 Gem用户界面CSS在Rails应用程序中30 Gem 04:45 Gem用于Python开发者闪电04:50PM网络事件轨道2: 09:00AM Ruby On Rails维护60min 10:00AM在Python 45min 10:45AM Ruby错误来自错误匹配的Gem 45min 11:30AM Lua Lua对于大众来说,30分钟12:00的午餐01:00下午10:00(在我的项目上)45分钟01:45 04 30分钟02:15下午坐下来写30min 02:45下午编程在西雅图的Boondocks 30min 03:15 04 Ruby for后端开发30分钟03:45PM一个没有HackerNews 30min 04:15的网络事件

我成功地完成了问题的设计,它工作得很完美,但我希望看到专家对我的代码的意见,并提供建议。

timing.py

代码语言:javascript
复制
from datetime import timedelta, datetime


class Timing:
    def __init__(self):
        self.morning_start = (datetime.min+ timedelta(hours=9)).strftime('%I:%M %p')
        self.lunch = (datetime.min+ timedelta(hours=12)).strftime('%I:%M %p')
        self.afternoon_start = (datetime.min+ timedelta(hours=13)).strftime('%I:%M %p')
        self.day_end = (datetime.min+ timedelta(hours=17)).strftime('%I:%M %p')

if __name__ == '__main__':
    a = Timing()
    print(a.afternoon_start)

track.py

代码语言:javascript
复制
from datetime import timedelta, datetime

from .timing import Timing


class Track(Timing):
    id = 0

    def __init__(self):
        super(Track, self).__init__()
        Track.id += 1
        self.talks = {}
        self.talk_list = Track.extract_input()

    @staticmethod
    def extract_input():
        __talks = {}
        lines = []
        try:
            lines = [line.strip() for line in open('test.txt')]
        except FileNotFoundError as e:
            print('File Not Found', e)
        for line in lines:
            title, minutes = line.rsplit(maxsplit=1)
            try:
                minutes = int(minutes[:-3])
            # negative indexing raises error, so it means it's lightning
            except ValueError:
                minutes = 5
            __talks[line] = minutes
        return __talks

    def get_talks(self, start_talk, end_talk):
        start = timedelta(hours=start_talk)
        for key, value in list(self.talk_list.items()):
            prev = start + timedelta(minutes=int(value))
            if prev <= timedelta(hours=end_talk):
                self.talks[(datetime.min + start).strftime('%I:%M %p')] = key
                self.talk_list.popitem()
                start += timedelta(minutes=int(value))
        return self.talks

    def show_output(self):
        while not len(self.talk_list) is 0:
            print('Track %s' % Track.id)
            self.__prepare_output(9, 12)
            print('%s - %s' % (self.lunch, 'Lunch'))
            self.__prepare_output(13, 17)
            print('%s - %s' % (self.day_end, 'Networking Event'))
            Track.id += 1

    def __prepare_output(self, start, end):
        for time, title in sorted(self.get_talks(start, end).items()):
            print(time, '-', title)
        # clear previous entries
        self.talks.clear()


if __name__ == '__main__':
    a = Track()
    a.show_output()
EN

回答 2

Code Review用户

发布于 2015-07-07 20:01:44

以下是一些一般性意见:

  • 对于空格要更加一致,特别是在操作符周围。它将使您的代码更容易阅读。
  • 对于您在计时对象中存储实例变量的方式,我有两个建议:
    • 每一行几乎是一样的。我认为最好有一个函数def time_after_start(小时):返回datetime.min + timedelta(hours=hours),并为每个函数调用它。它将使代码变得更清晰,并且更容易看出代码行之间的区别。
    • 我会将它们保留为datetime对象,并且只在您实际需要打印它们时将它们转换为字符串。使用字符串进行漂亮的打印,而不是存储结构化数据。如果以后需要修改这些变量,则必须先从字符串中解析它们。(我知道你在这里并没有改变他们,这只是一个我不喜欢的习惯。)

  • 您打开test.txt,但永远不要再次关闭它。你正在创建一个包含所有行的列表,这对内存来说效率很低。最好是一次只遍历一行,如下所示:使用open('test.txt')作为f: for行f:# do整行返回__talks -这是更有效的内存和惯用用法。
  • 我不知道为什么您觉得需要在talks变量上加上两个下划线;我认为它看起来很奇怪,并且会去掉它。
  • get_talks()中,您将self.talk_list.items()的结果转换为一个列表,我不知道为什么要这样做。可以直接在.items()上迭代,而不必首先将其转换为列表。同样,我们知道这些值是int的,因为我们在extract_input()中将它们设置为int‘s。因此,强制转换到int()只是多余的。
  • 与其在key, value上迭代,我选择的变量名称反映了字典中这些元素的含义。Self.talk_list.items()中的几分钟谈话如何:这将使您更容易遵循代码的意图。
  • show_output()中,if语句有点奇怪。我认为您想说的是“如果self.talk_list中还有元素,请继续”,这更好地表示为self.talk_list:我认为这更容易阅读。
票数 3
EN

Code Review用户

发布于 2015-07-07 18:25:04

首先,负索引在Python中确实有效,所以下面的except块永远不会执行。另外,当您尝试访问不存在的list元素时,它会引发IndexError,而不是ValueError

代码语言:javascript
复制
try:
    minutes = int(minutes[:-3])
# negative indexing raises error, so it means it's lightning
except ValueError:
    minutes = 5

为什么方法__talks中的变量extract_input以两个前导下划线为前缀?变量是函数的本地变量,因此不需要将其设置为“私有”。

最后,添加一些文档字符串来描述您的函数/类。Docstring是用来描述函数的特殊注释。一个示例docstring如下所示:

代码语言:javascript
复制
def my_func( ... ):
    """
    Describe what your function does
    in addition to it's arguments.
    """
    ...
票数 2
EN
页面原文内容由Code Review提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://codereview.stackexchange.com/questions/83193

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档