001    /*
002    @license.text@
003     */
004    package biz.hammurapi.util;
005    
006    import java.util.HashSet;
007    import java.util.LinkedList;
008    import java.util.Set;
009    
010    /**
011     * Visits class hierarchy in the order: class, implemented
012     * interfaces, superclass, superclass implemented interfaces, ...
013     * java.lang.Object is always visited last.
014     * @author Pavel Vlasov
015     * @revision $Revision$
016     */
017    public class ClassHierarchyVisitable implements Visitable {
018            private Class clazz;
019            
020            public ClassHierarchyVisitable(Class clazz) {
021                    this.clazz=clazz;
022            }
023            
024            public boolean accept(Visitor visitor) {
025                    LinkedList queue=new LinkedList();
026                    queue.add(clazz);
027                    Set visited=new HashSet();
028                    visited.add(Object.class);
029                    
030                    while (!queue.isEmpty()) {
031                            Class currentClazz=(Class) queue.removeFirst();
032                            if (visitor.visit(currentClazz)) {
033                                    Class[] interfaces = currentClazz.getInterfaces();
034                                    for (int i=0; i<interfaces.length; i++) {
035                                            if (visited.add(interfaces[i])) {
036                                                    queue.add(interfaces[i]);
037                                            }
038                                    }
039                                    
040                                    Class superclass = currentClazz.getSuperclass();
041                                    if (superclass!=null && visited.add(superclass)) {
042                                            queue.add(superclass);
043                                    }
044                            } else {
045                                    return false;
046                            }
047                    }
048                    
049                    return visitor.visit(Object.class);
050            }
051    
052    }