Java: extension of inner classes

I am trying to understand the extension of inner classes in Java. I read, but did not find anything, that answered my question. So here goes ...

I have...

public class Pie{ protected Slice[] slices; // Pie constructor public Pie(int n){ sliceGenerator(n) } private void sliceGenerator(int n){ slices = new Slice[n]; final float sweepAngle = 360.0f/(float)n; float startAngle = 0; for (int i=0;i<n;i++){ slices[i] = new Slice(startAngle); startAngle += sweepAngle; } } @Override public String toString(){ for (Slice s:slices){ s.toString(); } } // Inner class... public class Slice{ public Slice(float startAngle){ //set some private fields based on startAngle and generic pie } @Override public String toString(){ return **string based on private fields** } } } 

Then I expand it ...

 public class ApplePie extends Pie{ protected Slice[] slices; // Apple Pie constructor public ApplePie(int n){ super(n); } // Inner class... public class Slice extends Pie.Slice{ public Slice(float startAngle){ super(startAngle); //set some **additional** private fields based on startAngle **specific to apple pie** appleness or something } @Override public String toString(){ return **string based on apple pie specific private fields** } } } 

Now when I make an apple pie and call its toString method, like this ...

 ApplePie ap = new ApplePie(8); System.out.println(ap.toString()); 

I do not get information about slices of apple pie, but information about slices of pie. It ignores my redefinition of toString or, rather, ignores my Slice apple pie. How can I arrange it so that apple pie slices relate to ApplePie ?

Any help is much appreciated! Sorry for the links to the pie - this is the actual class I'm working with ...

+6
source share
3 answers

I changed the code to fit your requirements.

Your Pie superclass is about to create a new Slice instance, but the ApplePie Slice child class does not override the Slice method of its superclass.

I added functions below to allow the child class to create its own Slice .

 protected void newSliceArray(int n) { slices = new Slice[n]; } protected Slice newSlice(float startAngle) { return new Slice(startAngle); } 

Pie.java:

 public class Pie { private int a = 1; protected Slice[] slices; // Pie constructor public Pie(int n) { sliceGenerator(n); } private void sliceGenerator(int n) { newSliceArray(n); final float sweepAngle = 360.0f / n; float startAngle = 0; for (int i = 0; i < n; i++) { slices[i] = newSlice(startAngle); startAngle += sweepAngle; } } protected void newSliceArray(int n) { slices = new Slice[n]; } protected Slice newSlice(float startAngle) { return new Slice(startAngle); } @Override public String toString() { String t = ""; for (Slice s : slices) { t += s.toString(); } return t; } // Inner class... public class Slice { public Slice(float startAngle) { // set some private fields based on startAngle and generic pie } @Override public String toString() { return "" + a; } } } 

ApplePie.java:

 public class ApplePie extends Pie { private int b = 2; // protected Slice[] slices; // Apple Pie constructor public ApplePie(int n) { super(n); } protected void newSliceArray(int n) { slices = new Slice[n]; } protected Slice newSlice(float startAngle) { return new Slice(startAngle); } // Inner class... public class Slice extends Pie.Slice { public Slice(float startAngle) { super(startAngle); // set some **additional** private fields based on startAngle **specific to apple pie** // appleness or something } @Override public String toString() { return b + ""; } } } 

Test:

 public static void main(String[] args) { ApplePie ap = new ApplePie(8); System.out.println(ap.toString()); } 

The code will print 22222222

+3
source

In your superclass, you create and save Pie.Slice objects:

 private void sliceGenerator(int n){ slices = new Slice[n]; final float sweepAngle = 360.0f/(float)n; float startAngle = 0; for (int i=0;i<n;i++){ slices[i] = new Slice(startAngle); startAngle += sweepAngle; } } 

These are the same objects used by Pie.toString (which ApplePie does not cancel, by the way).

Extending Pie with ApplePie and extending Pie.Slice with ApplePie.Slice does not change this. new Slice(startAngle) in the above code does not magically switch to creating something else.

In addition, your Pie.toString() does not return anything - it should not even compile:

 @Override public String toString(){ for (Slice s:slices){ s.toString(); } } 

I assume that you want to return a string representing all the fragments. This would be a quick fix, for example:

 @Override public String toString() { return Arrays.toString(slices); } 

( Arrays.toString is just a utility method for getting a string representation of an array.)

0
source

The answer lies in your program. When you instantiate the Slice class, it calls the superclass and calls sliceGenerator. This method internally creates instances of Pie.Slice, not ApplePie.Slice. To work around this, make the sliceGenerator method secure and override it in the Apple.Slice class. Create instances of Apple.Slice and it should work.

0
source

All Articles