尝试从列表构建组织树

时间:2016-10-11 01:11:41

标签: python algorithm sorting parsing

我的输入文件格式如下。

Fred,Karl,Technician,2010--Karl,Cathy,VP,2009--Cathy,NULL,CEO,2007--
--Vince,Cathy,Technician,2010

我需要将这些信息解析到最终在输出文件中看起来像这样的地方:

Cathy (CEO) 2007
-Karl (VP) 2009
--Fred (Technician) 2010
-Vince (Technician) 2010

首席执行官处于最高位置,每个下属应该在他们的上级之下。所以不管第二个名字是什么,那就是主管。诀窍在于,如果一名员工有2名主管,他们需要缩进两次" - "以及他们的直接上司。

我试过遍历列表并解析" - "和逗号,但我在结构本身挣扎。这是我到目前为止所做的。

with open('org_chart_sample.in', 'r') as reader:  # Open the input file
with open('output.out', 'w') as writer:  # Make output file writable
    reader.readline()   # Ignore first line
    lines  = reader.readlines()  # Read input lines

    for line in lines:      # Parse out input by the -- which separated attributes of people in the org
        employees = line.split('--')
        hierarchy = []      # Exterior list to aid in hierarchy

        for employee in employees:  # Logic that adds to the hierarchy list as algorithm runs
            info = employee.split(',')
            hierarchy.append(info)

我已经坚持这个问题的时间更长了,我想承认:(

1 个答案:

答案 0 :(得分:0)

很酷的问题,工作很有趣。我试图彻底,它最终变得有点长,我希望它仍然可读。

代码:

##########################
#Input data cleaned a bit#
##########################
lines = ["Fred,Karl,Technician,2010",
         "Karl,Cathy,VP,2009",
         "Cathy,NULL,CEO,2007",
         "Vince,Cathy,Technician,2010",
         "Mary,NULL,CEO,2010",
         "Steve,Mary,IT,2013"]

##################################
#Worker class to make things neat#
##################################
class Worker(object):
    #Variables assigned to this worker
    __slots__ = ["name","boss","job","year","employees","level"]

    #Initialize this worker with a string in the form of:
    #"name,boss,job,year"
    def __init__(self,line):
        self.name,self.boss,self.job,self.year = line.split(",")
        self.level = 0 if self.boss == "NULL" else -1 #If boss is NULL, they are '0' level
        self.employees = []

    #A function to add another worker as this worker's employee
    def employ(self,worker):
        worker.level = self.level+1
        self.employees.append(worker)

    #This is a recursive function which returns a string of this worker
    #and all of this workers employees (depth first)
    def __repr__(self):
        rep_str = ""
        rep_str += "-"*self.level
        rep_str += str(self.name)+" works for "+str(self.boss)
        rep_str += " as a "+str(self.job)+" since "+str(self.year)+"\n"
        for employee in self.employees:
            rep_str += str(employee)
        return rep_str

########################################
#Prepare to assign the bosses employees#
########################################
#1. Turn all of the lines into worker objects
workers = [Worker(line) for line in lines]

#2. Start from the top level bosses (the ones that had NULL as boss)
boss_level = 0

#3. Get a list of all the workers that have a boss_level of 0
bosses = [w for w in workers if w.level == boss_level]

#While there are still boses looking to employ then keep going
while len(bosses) > 0:
    #For each boss look through all the workers and see if they work for this boss
    #If they do, employ that worker to the boss
    for boss in bosses:
        for worker in workers:
            if worker.level == -1 and boss.name == worker.boss:
                boss.employ(worker)

    #Move down a tier of management to sub-bosses
    #If there are no sub-bosses at this level, then stop, otherwise while loop again
    boss_level += 1
    bosses = [w for w in workers if w.level == boss_level]

##########################
#Printing out the workers#
##########################
#1. Loop through the top bosses and
#   print out them and all their workers
top_bosses = [w for w in workers if w.level == 0]
for top_boss in top_bosses:
    print top_boss

输出:

Cathy works for NULL as a CEO since 2007
-Karl works for Cathy as a VP since 2009
--Fred works for Karl as a Technician since 2010
-Vince works for Cathy as a Technician since 2010

Mary works for NULL as a CEO since 2010
-Steve works for Mary as a IT since 2013