初步模型,并没有实现换教练的。

import copy 
class student():
    def __init__(self,studentID,isAgent,leftNumsOfCourse,coach2id,coach3id):
        self.studentID = studentID
        self.isAgent = isAgent
        self.leftNumsOfCourse = leftNumsOfCourse
        self.coach2id = coach2id
        self.coach3id = coach3id
    def minusLeftNumsOfCourse(self,num):
        self.leftNumsOfCourse = self.leftNumsOfCourse - num
    def addLeftNumsOfCourse(self,num):
        self.leftNumsOfCourse = self.leftNumsOfCourse + num
#测试建立学生
student1 = student('u201010187',0,23,'c232','c432')
#print(student1.leftNumsOfCourse)
student1.minusLeftNumsOfCourse(3)
#print(student1.leftNumsOfCourse)

class coach():
    def __init__(self,coachid,teamID,coursesid,askForWeek):
        self.coachid = coachid
        self.teamID = teamID
        self.coursesid = coursesid    #list
        self.askForWeek = askForWeek   #list
    def isAbleToWork(self,day):
        self.askForWeek.append(day)

coach1 = coach('c2232','e33',[2,0,3],[])
#print(coach1.coursesid,coach1.askForWeek)
coach1.isAbleToWork('friday')
#print(coach1.askForWeek)

class schedule():
    def __init__(self,totalSchedule=[],query={}):
     #   self.coachid = coachid
        self.totalSchedule = totalSchedule
        self.query =query   #表索引字典
    def createBlankSchedule(self,numsOfCourseOneDay=17):  #创建一个新空的一个周期的空表
        daySchedule = [0 for i in range(numsOfCourseOneDay)]       
        weekSchedule = [copy.deepcopy(daySchedule) for i in range(7)]
        return weekSchedule
    def addCoachSchedule(self,coach,coachSchedule):#添加一个教练表到总教练表中
       # print(type(coach),coach.coachid)
        coachSchedule = copy.deepcopy(coachSchedule)
        numOfCoach = len(self.totalSchedule)
        self.query['%s'%coach.coachid] = numOfCoach #建立索引
        self.totalSchedule.append(coachSchedule)
    def scrapeSchedule(self,son_scheduleIndex=[]):
        #son_scheduleIndex = ['张三','李四','王五']
    #则返回的是张三李四王五教练的课表
        res = []
        newQuery ={}
        for coachID in son_scheduleIndex:
            index = self.query[coachID]
            numOfCoach = len(newQuery)
            newQuery[coachID] = numOfCoach
            res.append(self.totalSchedule[index])
        return res,newQuery
    def isCoachScheduleFull(self,coachname):
        coachindex = self.query(coachname)
        coachSchedule = self.totalSchedule[coachindex] #得到这个表
        for i in range(7):
            for j in range(17):
                if coachSchedule[i][j] ==0:
                    return False
        return True
    def searchContinuousNumsOfCourse(self,coachname,day):
        coachindex = self.query(coachname)
        coachSchedule = self.totalSchedule[coachindex]
        dayslice = coachSchedule[day]
        res = []
        for i in range(17):
            if dayslice[i]==0:
                res.append(i)
        return res  #输出的是[1,2,4,5,6,10,11,12,13,14...]
    def getScheduleOfCoach(self,coachname): #coachname就是coachid
        coachindex = self.query[coachname]
        coachSchedule = self.totalSchedule[coachindex] #得到这个表
        return coachSchedule
    def changeScheduleOfCourse(self,coachname,day,newslice):
        coachindex = self.query[coachname]
        print('要改变的coach在教练表中的索引是:',coachindex)
       # print('教练的某一天的表:',self.totalSchedule[coachindex][day])
        self.totalSchedule[coachindex][day] = newslice
       # print(self.totalSchedule)
        
    '''每个学员每天的上课数有下限,比如2,每个学员每个上课有上限,比如5
    '''
def canSatisfyRequirement12(dayslice):
    count = 0
    for i in range(17):
        if i ==0:
            count =1
            continue
        if dayslice[i] ==dayslice[i-1]:
            count += 1
        elif count <2:
            return False
        elif count >5:
            return False
        else:
            count = 1
    return True
    '''外地学员的开始和结束课节有限制,我们令限制为Beginninglimit,Endinglimit
    '''
def canSatisfyRequirement34(dayslice,student,Beginninglimit,Endinglimit):
    for i in range(Beginninglimit):
        if dayslice[i] == student.studentID:
            return False
    for j in range(Endinglimit,17):
        if dayslice[j] == student.studentID:
            return False
    return True
               
#schedule1 = schedule()

#print(schedule1.createBlankSchedule(17))

#def fitcoaches(student,totalschedule):
 #   coachID = student.coach2id
  #  '''得到这个教练的教练组,这个教练组的所有教练,是一个list
   # '''
    #teamCoach = ['张三','李四','王五']
    #scrapeSchedule = totalschedule.scrapeSchedule(teamCoach)
   # return student,scrapeSchedule
'''模拟排课的,输出是模拟排出的课,满足条件才会输出
   1,第一步判断是不是拆玩后学生的课表满足,要判断是不是超出了学生的接受范围
   2,检查填进去的slice是不是满足要求,逐个检测,报错就不行的,如果可以的话,就要写进入表了
     2.x检查临时表是不是时间段冲突,这需要定义一个函数
'''
def choice(student,schedule,coachname,day,studentArrangedSchedule):
    numsOfCourse = [5,4,3,2]
    slice1 = schedule.getScheduleOfCoach(coachname)[day]
   # print('+++no.1+++')
   # print('进入循环',slice1)
    preparedslice =[]
    for num in numsOfCourse:
     #   print('++++++no.%s+++++++'%num)
      #  print(slice1)
        if  num>student.leftNumsOfCourse:           
            continue  #循环进入下一个
        student.minusLeftNumsOfCourse(num) #修改进行判断
        if not isSuitableToStudent(student):
            student.addLeftNumsOfCourse(num)
            continue
        student.addLeftNumsOfCourse(num)  #修改回来
        #2的检测
        preparedslice = fullslice(slice1,num,student)
        if not canSatisfyRequirement12(preparedslice):
         #   print(slice1)
            print('没有满足条件12......')
            continue
        if student.isAgent ==1:            
            if not canSatisfyRequirement34(preparedslice,student,1,1):
                print('没有满足条件34.......')
                continue
        if isRepeat(studentArrangedSchedule,day,preparedslice):
            
            print('没有满足条件,跟已知学生课程时间冲突')
            continue
        #如果上面的条件都满足,就把这个数据写到schedule中,也就是原始表中改变slice1
                #学生的信息也改变,比如课时数
            '''这里还缺少一个维护学生上课是不是重复的表,考虑到学生是一个个进去选课的,所以这个可以用
            一个@@@@临时表@@@@维护,当学生选择上某课了,那么这个临时表就得更新
            
            '''
        schedule.changeScheduleOfCourse(coachname,day,preparedslice)
        student.minusLeftNumsOfCourse(num)
        print('更新前的表是:',studentArrangedSchedule)
        updateSchedule(studentArrangedSchedule,day,preparedslice)
        print('更新后的表是:',studentArrangedSchedule)
        return True
        break
    
  #  print("this slice is suitable")
   # print(preparedslice)
    return False    

'''填完课表后,学生的剩余课时数不能为1
    '''
def isSuitableToStudent(student):
    if student.leftNumsOfCourse ==1:
        return False
    else:
        return True

'''个人的课程是不是重复
schedule1----个人的历史课表
slice1----要检测的某天课程
'''
numsOfCourseOneDay =17
daySchedule = [0 for i in range(numsOfCourseOneDay)]
weekSchedule = [copy.deepcopy(daySchedule) for i in range(7)]
studentSchedule1 = weekSchedule
def isRepeat(studentSchedule1,day,slice1):
    for i in range(len(slice1)):  #追个检查是不是有重复安排的
        if (slice1[i] != 0 and studentSchedule1[day][i] !=0):
            return True
    return False
def updateSchedule(studentSchedule1,day,slice1):
    for i in range(len(slice1)):
        if slice1[i] !=0:
            studentSchedule1[day][i] = 1
'''
排列出一些位置选择
1,以学员角度,还是以课程为角度。
。。。。以课程的话,选择2,3,5优先选择多的,也就是5的,先检测5,然后检测3,再检测2
。。。。函数f(参数1,参数2,参数3)
            参数1,slice
            参数2,填的课,把0填成2或3或5
            参数3,学生对象
。。。。返回的是排好的slice1,或者返回0,表示本身课不行的
'''
def fullslice(slice1,numOfCourse,student):
    slice2 = copy.deepcopy(slice1)
    for i in range(17):
        if slice2[i]==0:
            slice2[i]=student.studentID
            numOfCourse = numOfCourse-1
        if numOfCourse ==0:
            break
    if numOfCourse ==0:
        return slice2
    else:
        return 0

schedule1 = schedule()
#print(schedule1.totalSchedule)
newtable = schedule1.createBlankSchedule(17)
coach1 = coach('c102','i234',1,[])
#print(coach1.teamID)
schedule1.addCoachSchedule(coach1,newtable)
#print(schedule1.totalSchedule)
coach2 = coach('c101','i234',1,[])
newtable = schedule1.createBlankSchedule(17)
schedule1.addCoachSchedule(coach2,newtable)
schedule1.changeScheduleOfCourse('c102',2,[2,2,1,1,0,0,1,1,1,0,0,0,5,5,0,0,0])
c = schedule1.totalSchedule
print('原始表:',schedule1.totalSchedule)
#print(schedule1.totalSchedule)
#print(schedule1.query)
#创建几个学生 studentID,isAgent,leftNumsOfCourse,coach2id,coach3id
student1 = student('s001',0,15,'c102','c232')
student2 = student('s002',0,3,'c102','c232')
for i in range(7):
    print('教练的第%s天'%i)    
    choice(student1,schedule1,'c102',i,studentSchedule1)
    print('学生剩余课数:',student1.leftNumsOfCourse)
    if student1.leftNumsOfCourse <2:
        break
print('后来表:',schedule1.totalSchedule)