两个类之间的递归java泛型

时间:2011-07-11 13:06:31

标签: java generics

这个问题类似于Possibly recursive Java generics between two classes中提出的问题。但是,就其他线程所述,一切正常。在我的例子中,我不幸地需要使用递归方法的其他类。

更具体一点:我想使用边和节点定义图类。然后,我想从图表类派生一个街道图,它使用道路和交汇点作为边和节点。另外,我想使用铁路和停靠点作为边缘和节点来导出公共交通图。最后,我想定义一个包含街道图或公共交通图的变量。最后一步是迄今为止我无法实现的目标。语言太多了;现在让我们来看看Java代码:

public interface Node<NT extends Node<NT, ET>, ET extends Edge<NT, ET>> {
  /* internal datastructures here */
}

public interface Edge<NT extends Node<NT, ET>, ET extends Edge<NT, ET>> {
  /* internal datastructures here */
}

public interface Graph<NT extends Node<NT, ET>, ET extends Edge<NT, ET>> {
  /* internal datastructures here */
}

public class JunctionNode implements Node<JunctionNode, RoadEdge> {
}

public class RoadEdge implements Edge<JunctionNode, RoadEdge> {
}

public class StreetGraph implements Graph<JunctionNode, RoadEdge> {
}

public class PTNode implements Node<PTNode, PTEdge> {
}

public class PTEdge implements Edge<PTNode, PTEdge> {
}

public class PTGraph implements Graph<PTNode, PTEdge> {
}

现在,到目前为止,这些定义。我想做的是:

StreetGraph street = new StreetGraph();
PTGraph ptGraph = new PTGraph();
Graph g = street;
...
g = ptGraph;
...
但是,我希望避免对原始类型等发出警告。所以显而易见的方法是:

Graph<Node, Edge> g = street;

然而,这是不可能的,因为Edge不是Node的ET的有效替代品(这对我来说是绝对清楚的)。我需要类似的东西:

Graph<NT = Node<ET>, ET = Edge<NT>> g;

这是(正如预期的)无效的Java代码。 任何想法,如何实现有效的Java代码没有警告/错误和类型安全?

任何帮助表示感谢。

谢谢, 的Matthias

2 个答案:

答案 0 :(得分:1)

正如Paulo所说,我认为通配符参数可能正是您所寻找的。

假设您的Graph界面具有这些方法

public interface Graph<NT extends Node<NT, ET>, ET extends Edge<NT, ET>> {
  public NT getNode();
  public ET getEdge();
}

并且您的StreetGraph以这种方式实现它们

public class StreetGraph implements Graph<JunctionNode, RoadEdge> {

    public RoadEdge getEdge()
    {
        return edge;
    }

    public JunctionNode getNode()
    {
        return node;
    }

}

然后你可以做到以下几点,所有类型安全和编译友好:

    Graph<?, ?> g = new PTGraph();
    g = new StreetGraph();

    Node<?, ?> n = g.getNode();
    Edge<?, ?> e = g.getEdge();

然后处理NodeEdge接口,与底层实现无关。

如果您需要额外的类型信息,例如如果您想访问特定于JunctionNode和RoadEdge但未包含在Node和/或Edge接口中的方法,那么您将使用更具体的StreetGraph而不是Graph<?, ?>

StreetGraph sg = new StreetGraph();
JunctionNode jn = sg.getNode();
RoadEdge re = sg.getEdge();

答案 1 :(得分:0)

PTGraphStreetGraph的常见超类型将是

Graph<?, ?>

这对你有用吗?