group结果转成table

class Tree:
converted = False
row = 0
def __init__(self):
self.value = None
self.num = 0
self.children_keys = []
self.children = {}
def create(self,parent,keys,i,n):
key = keys[i]
tree = parent.children.get(key)
if tree == None:
tree = Tree()
parent.children_keys.append(key)
parent.children[key] = tree
parent.num +=1
if i+1 == n:
tree.value = keys[n:]
tree.num = 1
else:
tree.create(tree,keys,i+1,n)

def travel(self,col):
for k in self.children_keys:
child = self.children.get(k)
r,c,h,w = self.convert(Tree.row,col,child.num,1)
s = "%s%s(%d,%d,%d,%d)"%("\t"*col,k,r,c,h,w)
if child.value:
r,c,h,w = self.convert(Tree.row,col,1,1)
s += "->"+self.print_values(r,c,child.value)
Tree.row += 1
print(s)
child.travel(col+1)

def print_values(self,row,col,values):
s = "["
i = 1
vs = []
for v in values:
r,c,h,w = self.convert(row,col+i,1,1)
vs.append("%d(%d,%d,%d,%d)"%(v,r,c,h,w))
i += 1
return "["+",".join(vs)+"]"

def convert(self,row,col,height,width):
return (col,row,width,height) if Tree.converted else (row,col,height,width)

class SimpleTree:
def __init__(self):
self.leaf = False
self.num = 0
self.row = 0
self.col = 0
self.index = 0
self.children_keys = []
self.children = {}

def create(self,parent,keys,i,n):
if i>=n: return
key = keys[i]
tree = parent.children.get(key)
if tree == None:
tree = SimpleTree()
parent.children_keys.append(key)
parent.children[key] = tree
parent.num +=1
if i+1 == n:
tree.leaf = True
tree.num = 1
else:
tree.create(tree,keys,i+1,n)

def calc_num(self):
self.num = 0
if self.leaf:
self.num = 1
else:
for k in self.children:
self.num += self.children.get(k).calc_num()
return self.num

def calc_postion(self,row,col):
self.row = row
self.col = col
if self.leaf: row += 1
for k in self.children_keys:
child = self.children.get(k)
row = child.calc_postion(row,col+1)
return row

def travel(self,positions,top,left,height,width,reverse):
for k in self.children_keys:
child = self.children.get(k)
r, c, h, w =top+child.row * height, left+child.col * width, child.num * height, width
if reverse:
r,c,h,w = c,r,w,h
s = "%s%s(%d,%d,%d,%d)"%("\t"*child.col,k,r,c,h,w)
positions[(r, c)] = (k, 1, 1)
print(s)
child.travel(positions,top,left,height,width,reverse)

def get_position(self,keys):
if len(keys) == 0:
return self.row,self.col
else:
return self.children.get(keys[0]).get_position(keys[1:])



def convert(self,row,col,height,width):
return (col,row,width,height) if Tree.converted else (row,col,height,width)

class Table:
def __init__(self,data,row_start,row_end,col_start,col_end,cell_horizon=True):
self.data = data
self.col_start = col_start
self.col_end = col_end
self.row_start = row_start
self.row_end = row_end
self.cell_horizon = cell_horizon
self.value_num = len(data[0]) - (col_end if col_end>row_end else row_end)

self.row_tree = self.create_tree(data, row_start, row_end)
self.col_tree = self.create_tree(data, col_start, col_end)

self.positions = {}
self.max_col = 0
self.max_row = 0

if cell_horizon:
self.row_tree.travel(self.positions,self.col_end-self.col_start, 0, 1, 1, False)
self.col_tree.travel(self.positions,self.row_end-self.row_start,0,self.value_num, 1, True)
else:
self.row_tree.travel(self.positions,self.col_end-self.col_start,0,self.value_num, 1, False)
self.col_tree.travel(self.positions,self.row_end-self.row_start,0,1, 1, True)

def get_cell_size(self):
if self.cell_horizon:
return self.col_end-self.col_start,self.row_end-self.row_start,1,self.value_num
else:
return self.col_end-self.col_start,self.row_end-self.row_start,self.value_num,1

def create_tree(self,data, start, end):
tree = SimpleTree()
for d in data:
tree.create(tree, d, start, end)
tree.calc_num()
tree.calc_postion(0, -1)
return tree

def cala_line_position(self,line):
r1,c1 = self.row_tree.get_position(line[self.row_start:self.row_end])
c2,r2 = self.col_tree.get_position(line[self.col_start:self.col_end])
# print(r1,c1,c2,r2)
return r1,c2

def set_max(self,r,c):
self.max_col = c if c > self.max_col else self.max_col
self.max_row = r if r > self.max_row else self.max_row

def cala_all_postion(self,top,left,height,width):
num = self.col_end if self.col_end>self.row_end else self.row_end
for line in self.data:
r,c = self.cala_line_position(line)
r,c = top+r*height,left+c*width

v = []
if height > 1:
for i in range(height):
v.append((r+i,c,1,1))
self.positions[(r+i, c)] = (line[num+i], 1, 1)
self.set_max(r+i, c)
elif width > 1:
for i in range(width):
v.append((r, c+i, 1, 1))
self.positions[(r, c+i)] = (line[num+i], 1, 1)
self.set_max(r, c+i)
else:
self.set_max(r,c)
self.positions[(r,c)] = (line[num],height,width)
print("%s->%s" % (str(line), (r, c, height, width)))
if len(v):
print("%s->%s" % (line,v))


def print_table(self):
for r in range(self.max_row+1):
s = ""
for c in range(self.max_col+1):
v = self.positions.get((r,c))
v = v[0] if v else '-'
s += "%s\t"%(v)
print(s)




data = [['a1','b1','c1','d1',1,2,3],
['a1','b1','c1','d2',1,2,3],
['a1','b1','c2','d1',4,5,6],
['a1','b1','c2','d2',7,8,9],
['a1','b2','c1','d1',11,12,13],
['a2','b1','c1','d1',14,15,16],
['a2','b1','c1','d2',17,18,19],
['a2','b1','c2','d1',21,22,23],
['a2','b1','c2','d2',24,25,26],
['a2','b2','c1','d1',27,28,29],
['a2','b2','c1','d2',31,32,33],
['a2','b2','c2','d1',34,35,36],
['a2','b2','c2','d2',37,38,39],
['a1','b2','c1','d2',41,42,43],
['a1','b2','c2','d1',44,45,46],
['a1','b2','c2','d2',47,48,49],

]

def test_tree(data):
tree = Tree()

for d in data:
tree.create(tree,d,0,4)
Tree.converted = True
tree.travel(0)

def test_simple_tree(data):
row_tree = create_tree(data,0,2,False)
col_tree = create_tree(data,2,4,True)


def test_table(data):
table = Table(data,0,2,2,4,True)
t,l,h,w = table.get_cell_size()
table.cala_all_postion(t,l,h,w)
table.print_table()



if __name__ == '__main__':
# test_simple_tree(data)
test_table(data)

posted on 2017-09-15 18:40  学而知之者  阅读(234)  评论(0编辑  收藏  举报