Java – how to get an inner class to inherit the generic type of the enclosing class?

I'm using java 6

Let my inner class use the same generic class as its closed class At present, I have

public class TernarySearchTree < T > {
    ...
    protected class TSTNode < T > {
        // index values for accessing relatives array
        protected static final int PARENT = 0,LOKID = 1,EQKID = 2,HIKID = 3; 
        protected char splitchar;
        protected TSTNode < T > [] relatives;
        private T data;

        protected TSTNode(char splitchar,TSTNode < T > parent) {
            this.splitchar = splitchar;
            relatives = new TSTNode[4];
            relatives[PARENT] = parent;
        }
    }
}

Now I get a warning

If I delete the type parameter from the inner class (i.e. delete < T > from the protected class tstnode < T > line), I get a compilation error on the lines related = new tstnode [4]

How to make everything right?

Solution

You can:

>Delete the < T > type parameter from tstnode (even if it becomes non generic) – it can still access the external < T > Rename the type parameter (say) u in the < T > class tstnode

[UPDATE]

Here are four different ways to rewrite code They all compile. I think you should consider using enummap (see version 4 below)

Version 1: use different named type parameters in inner classes You need to use a list instead of an array

public class TernarySearchTree<T> {

    protected class TSTNode<U> {
      // index values for accessing relatives array:
      protected static final int PARENT = 0,HIKID = 3;

      protected char splitchar;
      protected List<TSTNode<U>> relatives;
      private U data;

      protected TSTNode(char splitchar,TSTNode<U> parent) {
        this.splitchar = splitchar;
        relatives = new ArrayList<TSTNode<U>>();
        for (int i = 0; i < HIKID; ++i) {  // Allocate 4 slots in relatives
          relatives.add(null);
        }
        relatives.set(PARENT,parent);
      }          
    }

    private TSTNode<T> node; // When you use it,pass T as U

    public TernarySearchTree() {
      node = new TSTNode<T>(',',null);  // When you use it,pass T as U 
    }
  }

Version 2: inherit t from closed classes

public class TernarySearchTree<T> {

    protected class TSTNode {
      // index values for accessing relatives array:
      protected static final int PARENT = 0,HIKID = 3;

      protected char splitchar;
      protected List<TSTNode> relatives;
      private T data;

      protected TSTNode(char splitchar,TSTNode parent) {
        this.splitchar = splitchar;
        relatives = new ArrayList<TSTNode>();
        for (int i = 0; i < HIKID; ++i) {  // Allocate 4 slots in relatives
          relatives.add(null);
        }
        relatives.set(PARENT,parent);
      }
    }

    private TSTNode node; 

    public TernarySearchTree() {
      node = new TSTNode(',null);  
    }
  }

Version 3: use maps (not lists)

public class TernarySearchTree<T> {

    protected class TSTNode {
      // index values for accessing relatives array:
      protected static final int PARENT = 0,HIKID = 3;

      protected char splitchar;
      protected Map<Integer,TSTNode> relatives;
      private T data;

      protected TSTNode(char splitchar,TSTNode parent) {
        this.splitchar = splitchar;
        // Create a hash map. No need to pre-allocate!
        relatives = new HashMap<Integer,TSTNode>(); 
        relatives.put(PARENT,parent); // set -> put
      }
    }

    private TSTNode node; 

    public TernarySearchTree() {
      node = new TSTNode(',null);  
    }
  }
}

Version 4: defining indexes as enumerations using enunmap (instead of hash mapping)

public class TernarySearchTree<T> {

    protected static enum Index {
      PARENT,LOKID,EQKID,HIKID;
    }

    protected class TSTNode {    
      protected char splitchar;
      protected EnumMap<Index,TSTNode parent) {
        this.splitchar = splitchar;
        // Create an EnumMap. 
        relatives = new EnumMap<Index,TSTNode>(Index.class);
        relatives.put(Index.PARENT,parent); 
      }
    }

    private TSTNode node; 

    public TernarySearchTree() {
      node = new TSTNode(',null);  
    }
  }

[Update 2] one thing to remember: use enummap instead of ordinal indexing

The content of this article comes from the network collection of netizens. It is used as a learning reference. The copyright belongs to the original author.
THE END
分享
二维码
< <上一篇
下一篇>>