optimizations to IntPairMap.java
[sbp.git] / src / edu / berkeley / sbp / Tree.java
1 // Copyright 2006-2007 all rights reserved; see LICENSE file for BSD-style license
2
3 package edu.berkeley.sbp;
4 import edu.berkeley.sbp.*;
5 import edu.berkeley.sbp.util.*;
6 import java.io.*;
7 import java.util.*;
8 import java.lang.reflect.*;
9
10 /** <font color=blue>a tree (or node in a tree); see jargon.txt for details</font> */
11 public class Tree<NodeType>
12     extends PrintableTree<Tree<NodeType>>
13     implements Iterable<Tree<NodeType>> {
14
15     private final Input.Region     location;
16     private final NodeType         ihead;
17     private final Tree<NodeType>[] children;
18
19     /** the number of children the tree has */
20     public int               size() { return children.length; }
21
22     /** the element at the head of the tree */
23     public NodeType                 head()        { return ihead; }
24     public NodeType              getHead()        { return ihead; }
25
26     /** the tree's children */
27     public Iterable<Tree<NodeType>> children()    { return this; }
28
29     /** the tree's children */
30     public Iterator<Tree<NodeType>> iterator()    { return new ArrayIterator(children); }
31
32     /** get the <tt>i</t>th child */
33     public Tree<NodeType> child(int i)            { return children[i]; }
34
35     /** get the input region that this tree was parsed from */
36     public Input.Region    getRegion() { return location; }
37
38     public Tree(Input.Region loc, NodeType head)                            { this(loc, head, new Tree[0]); }
39     public Tree(Input.Region loc, NodeType head, Tree<NodeType>[] children) { this(loc, head, children, new boolean[children==null?0:children.length]); }
40
41     // FIXME: fairly inefficient because we keep copying arrays
42     /** package-private constructor, allows setting the "lift" bit */
43     Tree(Input.Region loc, NodeType head, Tree<NodeType>[] children, boolean[] lifts) {
44         this.location = loc;
45         this.ihead = head;
46
47         int count = 0;
48         for(int i=0; i<children.length; i++)
49             count += lifts[i] ? children[i].size() : 1;
50
51         this.children = new Tree[count];
52         int j = 0;
53         for(int i=0; i<children.length; i++) {
54             if (!lifts[i])
55                 this.children[j++] = children[i];
56             else
57                 for(int k=0; k<children[i].size(); k++)
58                     this.children[j++] = children[i].child(k);
59         }
60     }
61
62
63     // PrintableTree /////////////////////////////////////////////////////////////////////////////
64
65     protected String headToString() { return head()==null?null:head().toString(); }
66     protected String headToJava()   {
67       // FIXME
68         if (head()==null) return null;
69         if (head() instanceof ToJava) {
70             StringBuffer sb = new StringBuffer();
71             ((ToJava)head()).toJava(sb);
72             return sb.toString();
73         }
74         return (head()==null?"null":("\""+StringUtil.toJavaString(head().toString())+"\""));
75     }
76     protected String left()   { return "{"; }
77     protected String right()  { return "}"; }
78     protected boolean ignoreSingleton() { return false; }
79
80
81 }