Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
150 views
in Technique[技术] by (71.8m points)

How to color tree nodes with fixed set of colors?

I have a employee hierarchy tree that I want to apply colors for. I can only use at max 10 colors since more colors make it too confusing to users. What is the logic or algorithm I can use to color the tree with a set of colors? are there some techniques on how to do this? My initial thinking was to find 10 sub trees in the tree by doing a BFS and then color them differently. If there are >10 children at the first level itself, then don't apply any color and if there are < 10 nodes then keep going down till we find 10 subtrees to color. Is this the right way to look at this problem? Amy more ideas?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Do you want every adjacent node to be a different color? Parents different from all their children and siblings different from each other? With the colors otherwise randomly assigned?

The old code didn't meet the requirements I put on it and so I wrote a new version of the code that is much better as it is iterative. And I'm much more satisfied that it does what meets the description that I stated above.

If so then start out with the set of all colors C, pick one for the parent lets call that one P for each of the children going left to right color them out of the set C - {S,P} where S is the color of the left sibling of this node. Repeat this for each of the children with the set C - D where D is the color of this child except that you have already picked the color of the node.

Most of that is still true but instead of depth first recursion I switch to iterative level order traversal:

import random

class Node(object):

    def __init__(self, children):
        self.children = children
        self.color = None

    def __str__(self):
        return  '<node {}>'.format(self.color) + ' '.join(str(c) for c in self.children) + '</node>'

def pick(s):
    return random.choice(list(s))

def assign_colors(node, set_of_colors):

    node.color = pick(set_of_colors)

    level = [node]
    while level:

        left_sibling = set()
        _level = []
        for node in level:
            for child in node.children:
                _level.append(child)
                child.color = pick(set_of_colors - (set([node.color]) | left_sibling))
                left_sibling = set([child.color])

        level = _level

test = Node([Node([Node([Node([]), Node([]), Node([]), Node([])]),
             Node([Node([]), Node([])]), Node([]), Node([])]),
             Node([Node([]), Node([]), Node([]), Node([])]), Node([])])

assign_colors(test, set([1,2,3,4]))

print test

assign_colors(test, set([1,2,3,4,5]))

print test

The following is the reformatted output. Note that no child has the same color as its parent nor the same as its left sibling or child on the same level to its left.

<node 3>
    <node 4>
        <node 2>
            <node 4></node>
            <node 1></node>
            <node 4></node>
            <node 1></node>
        </node>
        <node 1>
            <node 4></node>
            <node 3></node>
        </node>
        <node 3></node>
        <node 1></node>
    </node>
    <node 1>
        <node 2></node>
        <node 3></node>
        <node 2></node>
        <node 4></node>
    </node>
    <node 2></node>
</node>
<node 4>
    <node 2>
        <node 1>
            <node 5></node>
            <node 4></node>
            <node 2></node>
            <node 4></node>
        </node>
        <node 5>
            <node 3></node>
            <node 2></node>
        </node>
        <node 4></node>
        <node 3></node>
    </node>
    <node 5>
        <node 1></node>
        <node 4></node>
        <node 2></node>
        <node 3></node>
    </node>
    <node 1></node>
</node>

Any tree can be colored with at most 3 colors (more just makes it more colorful). Consider:

          1
      /   |   
     2      3 2
  /  |  
  1 3 1 3
/ |   
3 2 3 2

That would be the tree equivalent of zebra striped tables. Hereby I name this zebra striped trees.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...