抽象类需要访问子类属性

时间:2012-11-05 22:44:41

标签: java abstract-class

我的代码有问题(编辑:这些类的完整代码)

public abstract class SimplePolygon implements Polygon {

  //protected Vertex2D[] varray; //this is wrong in tests
  public double getWidth(){
    double min = varray[0].getX(), max = varray[0].getX();

    for(int i = 0;i<varray.length;i++){
        max = Math.max(max,varray[i].getX());
        min = Math.min(min,varray[i].getX());
    }
    return max - min;
  }

  public double getHeight(){
    double min = varray[0].getY(), max = varray[0].getY();

    for(int i = 0;i<varray.length;i++){
        max = Math.max(max,varray[i].getY());
        min = Math.min(min,varray[i].getY());
    }
    return max - min;
  }

  public double getLength(){
    double distance = 0;
    for(int i = 0;i<varray.length;i++){
        if((i+1)<varray.length){distance += varray[i].distance(varray[i+1]);}
        else{distance += varray[i].distance(varray[0]);}
    }

    return distance;
  }

  public double getArea(){
    double suma = 0;
    for(int i = 0;i<varray.length-1;i++){
        suma += varray[i].getX()*varray[i+1].getY() - varray[i+1].getX()*varray[i].getY();
    }
    return suma/2;
  }

  public String toString(){
    String str = "Polygon: vertices ="; 
    for(int i = 0;i<varray.length;i++){
        str += " ";
        str += varray[i];
    }
    return str;
  }
}

public class ArrayPolygon extends SimplePolygon {

  public ArrayPolygon(Vertex2D[] array){
    varray = new Vertex2D[array.length];
    if (array == null){}
    for(int i = 0;i<array.length;i++){
        if (array[i] == null){}
        varray[i] = array[i];
    }
  }

  public Vertex2D getVertex(int index) throws IllegalArgumentException{
    return varray[index];
  }

  public int getNumVertices(){
    return varray.length;
  }

}

问题是,我不允许向抽象类SimplePolygon添加任何属性或方法,因此我无法正确初始化varray。它可以简单地用该类中受保护的属性来解决,但是由于某些(愚蠢的)原因我不能这样做。有没有人知道如何在没有它的情况下解决它?感谢您的帮助。

4 个答案:

答案 0 :(得分:1)

想一想:

  • 您的Polygon界面为java.util.List界面
  • 您的SimplePoygon抽象类java.util.AbstractCollection
  • 您的ArrayPolygon具体课程为java.util.ArrayList

我认为你的任务的重点是用迭代器实现一个解决方案,这样你就可以在抽象类中实现关于多边形的泛型方法,同时隐藏包含具体类中数据点的实际数据结构;这样:

/* 
 *   This class implements generic methods about polygon, like size, area and 
 *   so on, leveraging on the Vertex2D iterator.
 */
public abstract class SimplePolygon implements Polygon {

    // all concrete subclasses must implement iterator
    public abstract Iterator<Vertex2D> iterator();

    // this generic method prints the vertex list
    // using iterator hides the data structure used in implementation
    public String toString() {
       Iterator<Vertex2D> it = iterator();
       if (! it.hasNext())
           return "[]";

       StringBuilder sb = new StringBuilder();
       sb.append('Polygon: vertices = [');
       for (;;) {
           Vertex2D e = it.next();
           if (! it.hasNext())
               return sb.append("]").toString();
           sb.append(' ');
       }
    }
}

// for instance this concrete classes uses an ArrayList
public ArrayPolygon extends SimplePolygon {

    public Iterator<Vertex2D> iterator() {
       return new .....
    }
}

答案 1 :(得分:0)

首先,这个问题与toString()无关 - 这是无关紧要的。

您的问题似乎是“我如何从子类初始化varray?”。

一种方法是在超类中创建一个构造函数:

public abstract class SimplePolygon implements Polygon {

    protected SimplePolygon(int size) { 
        varray = new Vertex2D[size]; // initialization by super class
    }

    protected SimplePolygon() {} // initialization totally by subclass

}

然后调用构造函数必须适合从子类:

public class ArrayPolygon extends SimplePolygon {

    public ArrayPolygon(Vertex2D[] array) {
        varray = array; // use default constructor and initialize it from parameter
    }
}

其他没有传入数组的子类可以调用特殊的构造函数:

public class Square extends SimplePolygon {

    public Square() { // probably pass them in too
        super(4); // we know there's 4 vertices
    }
}


问题是一般似乎有点无意义 - 目前尚不清楚这项工作的目标是什么。

答案 2 :(得分:0)

如果需要访问子类变量,可以通过强制子类通过方法公开它来公开该变量。

public abstract class SimplePolygon implements Polygon {
  protected abstract Vertex2D[] getArray();

...

public String toString(){
    String str = "Polygon: vertices ="; 
    Vertex2D[] varray = getArray();
    for(int i = 0;i<varray.length;i++){
        str += " ";
        str += varray[i];
    }
    return str;
}

然后在你班上:

public class ArrayPolygon extends SimplePolygon
{
private Vertex2D[] varray;
public ArrayPolygon(Vertex2D[] array){
    super(array.length);
    varray = new Vertex2D[array.length];
    if (array == null){}
    for(int i = 0;i<array.length;i++){
        if (array[i] == null){}
        varray[i] = array[i];
    }

  @Override
  protected Vertex2D[] getArray() {return varray;}
  ...
}

答案 3 :(得分:0)

我最终意识到问题出在哪里。答案非常简单......它足以在类SimplePolygon中将方法getVertex和getNumVertices声明为抽象。这两种方法提供了来自varray的足够多的信息。所以整个技巧是将varray.length和varray [n]改为那些方法。感谢您的时间和帮助。