From eed78007f3174fa849429e5944aeae4e99a93dd1 Mon Sep 17 00:00:00 2001 From: Braeden Sowinski Date: Sat, 10 Sep 2022 12:50:32 -0700 Subject: [PATCH] debug step 4 --- scheduleGenerator/generator.py | 34 ++++++----- tinker.py | 106 ++++++++++++++++++++------------- util/debug.py | 4 ++ 3 files changed, 90 insertions(+), 54 deletions(-) create mode 100644 util/debug.py diff --git a/scheduleGenerator/generator.py b/scheduleGenerator/generator.py index 56b3ba3..7e577b6 100644 --- a/scheduleGenerator/generator.py +++ b/scheduleGenerator/generator.py @@ -8,6 +8,9 @@ from string import hexdigits from util.mockStudents import getSampleStudents from util.generateCourses import getSampleCourses +# Import other utilites +from util.debug import debug + ''' Block 1-5 is first semester while block 6-10 is second semester @@ -285,14 +288,16 @@ def generateScheduleV3( # Tally first and second semester sem1, sem2 = 0, 0 sem1List, sem2List = {}, {} + allSemBlockLens = [] for i in range(1, 11): + allSemBlockLens.append(len(running[f"block{i}"])) if i <= 5: sem1 += len(running[f"block{i}"]) sem1List[f"block{i}"] = running[f"block{i}"] - elif i > 5: + elif i > 5: sem2 += len(running[f"block{i}"]) sem2List[f"block{i}"] = running[f"block{i}"] - + # If there is more than one class Running if allClassRunCounts[index] > 1: blockIndex = 0 if sem1 <= sem2 else 5 @@ -306,7 +311,7 @@ def generateScheduleV3( while not classInserted: blockIndex += offset - if len(running[list(running)[blockIndex]]) < blockClassLimit: + if len(running[f'block{blockIndex+1}']) < blockClassLimit: running[list(running)[blockIndex]][cname] = { "CrsNo": course, "Description": emptyClasses[course][cname]["Description"], @@ -324,20 +329,12 @@ def generateScheduleV3( # If the class only runs once, place in semester with least classes elif allClassRunCounts[index] == 1: # Equally disperse into semesters classes - semBlocks = [] - offset = 1 - - # If sem1 is less than or equal to sem2, add to sem1 - if sem1 <= sem2: [semBlocks.append(len(block)) for block in sem1List] - - # If sem2 is less than sem1, add to sem2 - elif sem1 > sem2: [semBlocks.append(len(block)) for block in sem2List] # Get block with least classes - leastBlock = semBlocks.index(min(semBlocks)) + leastBlock = allSemBlockLens.index(min(allSemBlockLens)) + 1 cname = f"{course}-0" - running[f"block{leastBlock+offset}"][cname] = { + running[f"block{leastBlock}"][cname] = { "CrsNo": course, "Description": emptyClasses[course][cname]["Description"], "students": selectedCourses[cname]["students"], @@ -350,6 +347,15 @@ def generateScheduleV3( allClassRunCounts.remove(allClassRunCounts[index]) courseRunInfo.pop(list(courseRunInfo)[index]) + # Debug to json for analysis + if blockClassLimit == 40: + with open('./output/timetable-debug1.json', 'w') as outfile: + json.dump(running, outfile, indent=2) + + else: + with open('./output/timetable-debug2.json', 'w') as outfile: + json.dump(running, outfile, indent=2) + # Step 5 - Fill student schedule for block in running: @@ -531,7 +537,7 @@ def generateScheduleV3( # Update Student records with open(studentsDir, "w") as outfile: - json.dump(students, outfile, indent=2) + json.dump(students, outfile, indent=2) return running diff --git a/tinker.py b/tinker.py index aecc413..4f9353b 100644 --- a/tinker.py +++ b/tinker.py @@ -12,16 +12,20 @@ import sys from util.mockStudents import getSampleStudents from util.generateCourses import getSampleCourses +# Import other utilities +from util.debug import debug + # Import Algorithm from scheduleGenerator.generator import generateScheduleV3 done = False # consts -blockClassLimit = 68 - -print(f'\n>> Debug: Current blockClassLimit = {blockClassLimit}') +blockClassLimit = 40 +print() +debug(f'Current blockClassLimit = {blockClassLimit}') + def processing(msg: str): for c in itertools.cycle(['|', '/', '-', '\\']): if done: break @@ -56,37 +60,50 @@ if __name__ == '__main__': st = time() # Start time - t = threading.Thread(target=processing, args=('Collection student requests',)) - t.start() # Start animation - sampleStudents = getSampleStudents("./sample_data/course_selection_data.csv", True) - done = True # End Animation - print('\nStudent list generated.\n') - - t = threading.Thread(target=processing, args=('Collection Course Information',)) - done = False # reset animation - t.start() # Start animation - sampleCourses = getSampleCourses("./sample_data/course_selection_data.csv", True) - done = True # End Animation - print('\nCourse Information Collected.\n') + showError = False + noAnim = False + for e in sys.argv: + if e.lower() == 'showerror': showError = True + if e.lower() == 'noanim': noAnim = True - sleep(0.1) - t = threading.Thread(target=processing, args=('Processing',)) - done = False # reset animation - t.start() # Start animation - timetable = {} - timetable["Version"] = 3 - timetable["timetable"] = generateScheduleV3(sampleStudents, sampleCourses, blockClassLimit, "./output/students.json", "./output/conflicts.json") + if noAnim: + sampleStudents = getSampleStudents("./sample_data/course_selection_data.csv", True) + sampleCourses = getSampleCourses("./sample_data/course_selection_data.csv", True) + timetable = {} + timetable["Version"] = 3 + timetable["timetable"] = generateScheduleV3(sampleStudents, sampleCourses, blockClassLimit, "./output/students.json", "./output/conflicts.json") + else: + t = threading.Thread(target=processing, args=('Collection student requests',)) + t.start() # Start animation + sampleStudents = getSampleStudents("./sample_data/course_selection_data.csv", True) + done = True # End Animation + print('\nStudent list generated.\n') - done = True # End Animation + + t = threading.Thread(target=processing, args=('Collection Course Information',)) + done = False # reset animation + t.start() # Start animation + sampleCourses = getSampleCourses("./sample_data/course_selection_data.csv", True) + done = True # End Animation + print('\nCourse Information Collected.\n') + + sleep(0.1) + t = threading.Thread(target=processing, args=('Processing',)) + done = False # reset animation + t.start() # Start animation + timetable = {} + timetable["Version"] = 3 + timetable["timetable"] = generateScheduleV3(sampleStudents, sampleCourses, blockClassLimit, "./output/students.json", "./output/conflicts.json") + + done = True # End Animation + et = time() # End time elapsed_time = round((et - st), 3) # Execution time print(f'\n\nDone - Finished in {elapsed_time} seconds\n') - for e in sys.argv: - if e.lower() == 'showerror': - errors, _, _ = errorOutput(sampleStudents) - print(errors) - break + if showError: + errors, _, _ = errorOutput(sampleStudents) + print(errors) with open("./output/timetable.json", "w") as outfile: json.dump(timetable, outfile, indent=2) @@ -94,6 +111,12 @@ if __name__ == '__main__': elif sys.argv[1].lower() == "no_refresh": print() + showError = False + noAnim = False + for e in sys.argv: + if e.lower() == 'showerror': showError = True + if e.lower() == 'noanim': noAnim = True + st = time() # Start time if not file_exists('./output/students.json') or not file_exists('./output/courses.json'): @@ -108,22 +131,25 @@ if __name__ == '__main__': for i in range(1, 11): student["schedule"][f"block{i}"] = [] student["classes"] = 0 - t = threading.Thread(target=processing, args=('Processing',)) - t.start() # Start animation - timetable = {} - timetable["Version"] = 3 - timetable["timetable"] = generateScheduleV3(sampleStudents, sampleCourses, blockClassLimit, "./output/students.json", "./output/conflicts.json") - - done = True # End Animation + if noAnim: + timetable = {} + timetable["Version"] = 3 + timetable["timetable"] = generateScheduleV3(sampleStudents, sampleCourses, blockClassLimit, "./output/students.json", "./output/conflicts.json") + else : + t = threading.Thread(target=processing, args=('Processing',)) + t.start() # Start animation + timetable = {} + timetable["Version"] = 3 + timetable["timetable"] = generateScheduleV3(sampleStudents, sampleCourses, blockClassLimit, "./output/students.json", "./output/conflicts.json") + done = True # End Animation + et = time() # End time elapsed_time = round((et - st), 3) # Execution time print(f'\n\nDone - Finished in {elapsed_time} seconds\n') - for e in sys.argv: - if e.lower() == 'showerror': - errors, _, _ = errorOutput(sampleStudents) - print(errors) - break + if showError: + errors, _, _ = errorOutput(sampleStudents) + print(errors) with open("./output/timetable.json", "w") as outfile: json.dump(timetable, outfile, indent=2) diff --git a/util/debug.py b/util/debug.py new file mode 100644 index 0000000..b55ccf3 --- /dev/null +++ b/util/debug.py @@ -0,0 +1,4 @@ +#!/usr/bin/env python + +# Define global debug function +debug = lambda msg : print(f">> Debug: {msg}") \ No newline at end of file