美文网首页
Python正式课第十二天

Python正式课第十二天

作者: code与有荣焉 | 来源:发表于2019-11-19 20:14 被阅读0次

    一、练习:python自定义日期类型(补充)

    class MyDate:
        def __init__(self,year,month,day):
            self.__normal_year = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
            self.__leap_year = [31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
            self.not_leap = 1
            if self.check(year,month,day) == True:
                self.__year = year
                self.__month = month
                self.__day = day
            else:
                raise ValueError('不是一个有效的日期')
    
    
        def check(self,year,month,day):
            if year < 0:
                return False
            if month > 12 or month < 1:
                return False
            if year % 4 == 0 and year % 100 != 0 or year % 400 == 0:
                self.not_leap = 0
                if day < 1 or day > self.__leap_year[month-1]:
                    return False
            else:
                if day < 1 or day > self.__normal_year[month - 1]:
                    return False
            return True
    
        def __str__(self):
            return f'{self.__year}-{self.__month}-{self.__day}'
    
        @property
        def year(self):
            return self.__year
    
        @year.setter
        def year(self,year):
            self.__year = year
    
        @property
        def month(self):
            return self.__month
    
        @month.setter
        def month(self, month):
            self.__month = month
    
        @property
        def day(self):
            return self.__day
    
        @day.setter
        def day(self, day):
            self.__day = day
    
    
        # d1 = MyDate()
        # d2 = MyDate()
        # d1.compare(d2)
        # 0 ---> 相等 -1 ---》小于 1 ----》大于
        def compare(self,other):
            if self.__year > other.year:
                return 1
            elif self.__year == other.year:
                if self.__month > other.month:
                    return 1
                elif self.__month == other.month:
                    if self.__day == other.day:
                        return 0
                    elif self.__day > other.day:
                        return 1
                    else:
                        return -1
                else:
                    return -1
            else:
                return -1
    
        # d1 = MyDate(2016,10,12)
        # dnew = d1.add_days(145)
        # dnew = 20161106
        def add_days(self, day_plus):
            templst = []
            while day_plus > 0:
                if self.not_leap == 0:
                    templst = self.__leap_year
                else:
                    templst = self.__normal_year
                #加的天数没有超过本月总天数
                if templst[self.month - 1] >= self.day + day_plus:
                    self.day += day_plus
                    day_plus = 0
                # 加的天数超过了本月总天数,但是没有超过本年剩余天数?
                else:
                    #本年还剩的天数
                    total = 0
                    for i in range(self.month,12):
                        total += templst[i]
    
                    day_plus -= (templst[self.month-1] - self.day)
                    #年不用动
                    if total >= day_plus:
                        while day_plus > 0:
                            self.month += 1
                            if day_plus > templst[self.month-1]:
                                day_plus -= templst[self.month-1]
                            else:
                                self.day = day_plus
                                day_plus = 0
                    else:
                        day_plus -= total
                        day_plus -= 1
                        self.year += 1
                        self.month = 1
                        self.day = 1
                        if self.year % 4 == 0 and self.year % 100 != 0 or self.year % 400 == 0:
                            self.not_leap = 0
    
        def add_day(self, num):
            while num:
                if self.year % 4 == 0:
                    if self.day < self.__leap_year[self.month - 1]:
                        self.day += 1
                        num -= 1
    
                    else:
                        if self.month < 12:
                            self.month += 1
                            self.day = 1
                            num -= 1
    
                        else:
                            self.year += 1
                            self.month = 1
                            self.day = 1
                            num -= 1
    
                else:
                    if self.day < self.__normal_year[self.month - 1]:
                        self.day += 1
                        num -= 1
    
                    else:
                        if self.month < 12:
                            self.month += 1
                            self.day = 1
                            num -= 1
    
                        else:
                            self.year += 1
                            self.month = 1
                            self.day = 1
                            num -= 1
                self.__init__(self.year, self.month, self.day)
        # d1 = MyDate(2016,10,12)
        # d2 = MyDate(2016,12,12)
        # days = d1.cal_interval(d2)----> d1-d2
        # days---60
        def cal_interval(self,date):
            interval = 0
            tmp = self
            isSmall = False
            if tmp.compare(date) == 0:
                return interval
            elif tmp.compare(date) < 0:
                isSmall = True
                tmp,date = date,tmp
    
            while tmp.compare(date) > 0:
                date.add_days(1)
                interval += 1
    
            if isSmall:
                return -interval
            else:
                return interval
    
        def get_day_in_the_year(self):
            sum = 0
            templst = []
            if self.not_leap == 0:
                templst = self.__leap_year
            else:
                templst = self.__normal_year
    
            for month in range(self.__month-1):
                sum += templst[month]
    
            sum += self.__day
            return sum
    
    if __name__ == '__main__':
        d1 = MyDate(1988,5,31)
        print(d1)
    
        d2 = MyDate(1988,8,31)
        print(d2)
    
        print(d1.cal_interval(d2))
    
        print(d2.compare(d1))
        d = MyDate(2019,11,19)
        print(d.get_day_in_the_year())
        print(d)
        d.add_day(110)
        print(d)
    
    

    二、综合练习:综合实战---东软睿道运营仿真

    需求 使用python面向对象思想,模拟仿真东软睿道公司运营整个过程

    两个目的
    - 综合运用学习过的知识点
    - 运用面向对象思维解决实际问题
    模拟睿道培训机构,从招生,到开班,到学员学习课程,到学员毕业,计算公司总收入,统计学员人数
    一.类的识别
    1.学生类
    2.班级类
    3.课程类
    4.睿道公司类
    5.收入明细类:
    二.类的成员的定义(包括属性和方法)
    1.学生类Student:姓名,经验值,勤奋程度(0.9),聪明程度(1.9),是否进入班级(true)
    2.班级类Class:学员列表(List<Student>),开班日期,
    3.课程类Course:课程名称,课时。
    4.睿道公司类Company:班级列表(List<Class>)
    ,课程列表(List<Course>),总收入,收入明细。学员列表,未进入班级的学员列表
    5.收入明细类:收入金额,收入日志
    三.类的成员方法的定义
    1.学生类:学习,缴费
    2.班级类:开班,关班,上课
    3.课程类:课程名,课时
    4.睿道公司类:统计在校人数,统计全年收入,统计班级数....
    5.收入明细类:
    四.启动一个定时器,模拟东软睿道公司的运营情况
    每一秒执行一个timer函数,模拟睿道一天的运营状况(睿道的一天):
    1.招生(随机生成一个个学员对象,加入未开班班级,调用学员的缴费方法)
    2.开班(需要判断是否满足条件[学员数量达到某个阈值])
    3.各班级上课。(判断关班[所有课程全部完毕])
    

    Course.py

    class Course:
        def __init__(self,course_name,course_hour):
            self.course_name = course_name
            self.course_hour = course_hour
    
        def __str__(self):
            return self.course_name
    
    

    CourseTable.py

    from Course import Course
    
    
    class CourseTable:
        def __init__(self):
            self.tables = []
            self.tables.append(Course("python", 5))
            self.tables.append(Course("mysql", 3))
            self.tables.append(Course("flask", 5))
            self.tables.append(Course("django", 3))
            self.tables.append(Course("tensorflow", 5))
            self.tables.reverse()
    

    Student

    # 学生类Student:姓名,经验值,勤奋程度(0.9),聪明程度(1.9),是否进入班级(true)
    # 学生类:学习,缴费
    
    class Student:
        def __init__(self):
            self.name = ''
            self.point = 0
            self.hard_degree = 0
            self.smart_degree = 0
            self.is_enter_class = False
            
        def pay_money(self):
            return 20000
    
        def study(self):
            if self.is_enter_class == True:
                self.point += 10 * self.hard_degree * self.smart_degree
                print(f'{self.name}的经验值已经增长到{self.point}')
    
    

    NeuEduClass.py

    
    
    from datetime import datetime
    from CourseTable import CourseTable
    # // 2.班级类Class:学员列表(List<Student>),开班日期,班级名称
    # //2.班级类:开班,关班,上课
    # print(datetime.now())
    class NeuEduClass:
        class_num = 0
        def __init__(self):
            NeuEduClass.class_num += 1
            self.class_name = ''
            self.start_date = datetime.now()
            self.students = []
            self.course_table = CourseTable()
    
        # //从课程表里取出一个课程,该课程课时减1,判断课时是否为0,如果大于0,重新放回课程表,
        # //如果课程表为空,关闭班级
        # stand_up函数返回一个值,is_closed,代表是否需要关班
        def stand_up(self):
            is_closed = False
    
            cls = self.course_table.tables.pop()
            cls.course_hour -= 1
            print(f'{self.class_name}正在上{cls.course_name},还有{cls.course_hour}')
    
            if cls.course_hour > 0:
                self.course_table.tables.append(cls)
    
            if len(self.course_table.tables) == 0:
                is_closed = True
    
            return is_closed
    

    IncomeRecord

    
    # //收入金额,收入日志
    # //收到张三 10000
    # //收到李四 10000
    # //收到王五 10000
    
    class IncomeRecord:
        def __init__(self):
            self.income = 0
            self.log = ''
            self.datetime = None
    

    Company.py

    
    # //4.睿道公司类Company:班级列表(List<Class>)
    # //,课程列表(List<Course>),总收入,收入明细(List<IncomeRecord>)。学员列表,未进入班级的学员列表
    #     //睿道公司类:统计在校人数,统计全年收入,统计班级数....
    from datetime import datetime
    import random
    from time import time
    
    from IncomeRecord import IncomeRecord
    from NeuEduClass import NeuEduClass
    from Student import Student
    
    
    class Company:
        def __init__(self):
            self.classes = []
            self.income = 0
            self.income_records = []
            self.inschool_students = []
            self.noclass_students = []
            self.num = 5
    
        #向学员收费
        def add_money(self,student:Student):
            money = student.pay_money()
            self.income += money
    
            ir = IncomeRecord()
            ir.income = money
            ir.datetime = datetime.now()
            ir.log = f'{ir.datetime}收到{student.name}学费{money}元'
    
            self.income_records.append(ir)
    
        # 加入一个学生到未上课学员列表,考察当前列表长度,如果大于等于2人,开班(创建一个班级类对象,将学员添加到该班级)
        def add_student_to_noclasslist(self,student:Student):
            self.noclass_students.append(student)
    
            size = len(self.noclass_students)
            print(f'当前招生人数为{size}')
    
            if size >= self.num:
                #新建一个班级
                class_new = NeuEduClass()
                class_new.class_name = f'东软睿道Python{NeuEduClass.class_num}班'
                self.classes.append(class_new)
    
                print(f'{class_new.start_date}:{class_new.class_name}开班了')
    
                #转移学生---》NeuEduClass(self.students)
                for stu in self.noclass_students:
                    stu.is_enter_class = True
                    class_new.students.append(stu)
    
                self.noclass_students.clear()
    
        # //招生
        # //new 一个学生对象,返回。
        # //随机产生一个学员,先生成一个0-1之间的随机数
        # //如果该随机数小于0.7,就返回一个新学员对象
        # //否则,None
        # 招生成功率70 %
        # 返回值是一个学生对象(如果招生成果),是一个None(如果招生失败)
        def get_student(self):
            num = random.randint(1,10)
            if num <= 7:
                # // 根据系统当前时间生成一个时间戳,保证用户名不重复
                # // 时间戳是当前时间距离19700101经过的毫秒数
                stu = Student()
                stu.name = f'张{time()}'
                stu.point = num * 10
                stu.hard_degree = random.randint(1,10)
                stu.smart_degree = random.randint(1,10)
                stu.is_enter_class = False
                print(f'学员{stu.name}加入睿道学习,等待新班')
                return stu
            else:
                print(f'很遗憾,本次招生没有成功')
                return None
    
    

    day_of_neuedu.py

    
    import threading
    import time
    
    from Company import Company
    
    # //        四.在main函数中启动一个定时器,模拟我们睿道公司的运营情况
    # //        每一秒执行一个timer函数模拟睿道一天的运营状况(睿道的一天)。
    #                 0.判断一下今天是否休息
    # //            1.招生(随机生成一个个学员对象,加入为开班班级,调用学员的缴费方法);
    # //            2.开班(需要判断)
    # //            3.各班级上课。(判断关班)
    
    index = 0
    def day_of_neuedu(company:Company):
        global index
        index += 1
    
        #周末盘点
        if index % 7 == 0:
            stu_num = len(company.income_records)
            total_income = sum(map(lambda x: x.income,company.income_records))
            print('-' * 30 + f'周末休息盘点' + '-' * 30)
            print(f'\033[1;35m截止目前睿道共培训学员{stu_num}名,公司总营收收入{total_income}元\033[0m')
            print('-' * 30 + f'周末休息盘点' + '-' * 30)
            time.sleep(3)
        else:
            print('-' * 30 + f'东软睿道美好的一天开始了,各部门员工紧张忙碌了起来' + '-' * 30)
    
            print('市场部开始接待客户')
            stud = company.get_student()
            if stud != None:
                company.add_money(stud)
                company.add_student_to_noclasslist(stud)
    
            print(f'当前有{len(company.classes)}在上课')
    
            if len(company.classes) > 0:
                print('实施部的老师们开始上课了')
    
            class_removed = [] #待关闭的班级
            for cls in company.classes:
                is_closed = cls.stand_up()
                for stu in cls.students:
                    stu.study()
    
                if is_closed == True:
                    class_removed.append(cls)
    
            for del_cls in class_removed:
                print(f'{del_cls.class_name}学生结业了,全部找到高薪工作,走上人生巅峰,迎娶白富美')
                company.classes.remove(del_cls)
    
        timer = threading.Timer(6, day_of_neuedu, [company])
        timer.start()
    
    
    company = Company()
    timer = threading.Timer(6,day_of_neuedu,[company])
    timer.start()
    

    三、补充:Python中的计时器

    注意:

    • 其他语言中:一次性定时器,周期性定时器
    • Python中:只有一次性定时器
    #引入库 threading
    import threading
    #定义函数
    def fun_timer(msg,count):
        print('hello timer'+msg+str(count))   #打印输出
        global timer  #定义变量
        timer = threading.Timer(1,fun_timer,[msg,count])   
        timer.start()    #启用定时器
    
    
    #定时器构造函数主要有2个参数,第一个参数为时间处理函数(多少秒运行一次),第二个参数为时间处理函数函数名
    #第三个参数为传递给fun_timer的参数列表
    #1秒后调用函数fun_timer
    timer = threading.Timer(1,fun_timer,['hello',5])  #首次启动
    timer.start()
    

    四、异常处理

    1.异常的概念

    • 程序在运行时,如果 Python 解释器 遇到 到一个错误,会停止程序的执行,并且提示一些错误信息,这就是 异常
    • 程序停止执行并且提示错误信息 这个动作,我们通常称之为:抛出(raise)异常

    2. 异常捕获完整语法

    try:
        # 尝试执行的代码
        pass
    except 错误类型1:
        # 针对错误类型1,对应的代码处理
        pass
    except 错误类型2:
        # 针对错误类型2,对应的代码处理
        pass
    except (错误类型3, 错误类型4):
        # 针对错误类型3 和 4,对应的代码处理
        pass
    except Exception as result: # 包括其他所有情况
        # 打印错误信息
        print(result)
    else:
        # 没有异常才会执行的代码
        pass
    finally:
        # 无论是否有异常,都会执行的代码
        print("无论是否有异常,都会执行的代码")
    

    注意:

    • else 只有在没有异常时才会执行的代码
    • finally 无论是否有异常,都会执行的代码
    • 异常处理 try 之后 except 和 else 只能进一个
    • finally一般用来关闭文件或者释放内存
      示例:
    try:
        num = int(input("请输入整数:"))
        result = 8 / num
        print(result)
    except ValueError:
        print("请输入正确的整数")
    except ZeroDivisionError:
        print("除 0 错误")
    except Exception as result:
        print("未知错误 %s" % result)
    else:
        print("正常执行")
    finally:
        print("执行完成,但是不保证正确")
    

    3. 抛出 raise 异常

    主动抛出异常,没有异常创造异常也要异常。
    应用于某些场景需要特定条件才能进入,不达到条件则主动抛出异常。
    示例:

    def input_password():
    
        # 1\. 提示用户输入密码
        pwd = input("请输入密码:")
    
        # 2\. 判断密码长度,如果长度 >= 8,返回用户输入的密码
        if len(pwd) >= 8:
            return pwd
    
        # 3\. 密码长度不够,需要抛出异常
        # 1> 创建异常对象 - 使用异常的错误信息字符串作为参数
        ex = Exception("密码长度不够")
    
        # 2> 抛出异常对象
        raise ex
    
    try:
        user_pwd = input_password()
        print(user_pwd)
    except Exception as result:
        print("发现错误:%s" % result)
    

    4. 自定义异常

    class MyException(Exception):                   #让MyException类继承Exception
        def __init__(self,name,age):
            self.name = name
            self.age = age
    try:
        #知识点:主动抛出异常,就是实例化一个异常类
        raise MyException("zhansgan",19)            #实例化一个异常,实例化的时候需要传参数
    except MyException as obj:                      #这里体现一个封装,
        print(obj.age,obj.name)                     #捕获的就是MyException类携带过来的信息
    
    except Exception as obj:                        #万能捕获,之前的可能捕获不到,这里添加Exception作为保底
        print(obj)
    

    补充:
    打印彩色输出:

    print(f'\033[1;35m粉色啦啦啦\033[0m')
    

    相关文章

      网友评论

          本文标题:Python正式课第十二天

          本文链接:https://www.haomeiwen.com/subject/vcegictx.html