修改 subclass 中的 class 数组

modify class array in subclass

Dog class 有一个大小为 3 的数组,其中包含四个字符串值。但是,在 subclass GreatDane 中,我必须向同一个数组再添加一个元素。我必须在不使用数组列表的情况下执行此操作(我的 Java 课程尚未涵盖这些内容)。

这里是 class:

abstract class Dog {

String mSize [] = {"tiny", "small", "average", "large"};

int mFeedCounter;

int dogSize = 0;

String getSize() {
        return mSize[dogSize];
    }

    /*
     * setSize
     * Sets the size of the Dog
     * @param size the new size of the Dog, a String
     * @return nothing
     */
    void setSize(String size) {
        mSize[dogSize] = size;
    }

这是子 class:

Define the GreatDane class below
 *
 *  Great Danes have an extra size category, "huge".
 *  After growing to a "large" size, they may grow
 *  to an additional, "huge" size after 3 meals.
/************************************************/
class GreatDane extends Dog{
      String mSize[] = {"tiny","small","average","large","huge"};

    @Override
    void feed(){
        if(++mFeedCounter == 3){
        dogSize ++;
        getSize();
        mFeedCounter = 0;}
      }
    }

我尝试使用 mSize = new String []{"tiny","small","average","large","huge"}; 重新分配数组引用,但这只是给了我一个标识符预期错误。

无论如何,我不知道大丹犬为什么不搬到 mSize[4]

作为参考,这里有另一个 class 具有类似的有效方法:

class Chihuahua extends Dog{
    @Override
    void feed(){
        if(++mFeedCounter ==5){
        dogSize++;
        getSize();
        mFeedCounter = 0;}
    }
}

在您的 GreateDane 构造函数中,您可以像下面这样更改 Super 的 mSize 的引用:

GreatDane() {
    String mSize[] = new String[5];//define string array of size 5
    System.arraycopy(super.mSize, 0, mSize, 0, super.mSize.length);//copy existing elements from parent class
    mSize[4] = "huge";//add new elements at the end
    super.mSize = mSize;//change reference of super now as you dont want two copies of the same array in parent and child.
}

首先,抛开这对于这个用例来说是一个不合适的设计,如果你想让你的子classes能够修改mSize引用的数组,你应该声明它protected 访问,而不是包私有(默认)访问:

protected String[] mSize = {"tiny", "small", "average", "large"}; //Brackets are idiomatically placed after type, not name, in Java.

You can read more about access modifiers here. 然后,所有子classes(不只是在同一个包中的子,就像你的一样)可以修改它。您的尝试没有成功,因为它创建了一个新变量 mSize,巧合的是与 DogmSize 同名,但完全不同。由于您在 class Dog 中定义了 getSize(),它指的是 DogmSize,而不是 GreatDanemSize .相反,用 mSize = new String [] {"tiny","small","average","large","huge"}; 重新赋值是正确的,但是你收到了一个错误,因为你不能简单地将代码语句放在任何地方。您需要将语句放在构造函数中:

//these classes and methods should be public (also in Dog)
public class GreatDane extends Dog {
    public GreatDane() {
        mSize = new String[]{"tiny","small","average","large","huge"};
    }

    @Override
    public void feed(){
        mFeedCounter++;//incrementing inside other statements is concise but discouraged
        if (mFeedCounter == 3) { //consider >= 3 just in case
            dogSize++;
            getSize();
            mFeedCounter = 0;
        }
    }
}

或在初始化程序块中:

public class GreatDane extends Dog {
    {
        mSize = new String[]{"tiny","small","average","large","huge"};
    }

    @Override
    public void feed() {
        ...

很难说哪个版本更正确,因为这个设计本来就没有意义。 mSize 理论上应该替换为引用 static 数组的 getSizeDescription 方法,并且在 classes 中被覆盖,描述额外的尺寸,或者支持所有可能的尺寸但狗错误类型禁止长得太大。