Java - Need help to solve a bug - java

I am currently learning Java and for my inner classes practice, I played aroud the following code:
public class DataStructure {
// Create an array
private final static int SIZE = 15;
private int[] arrayOfInts = new int[SIZE];
public DataStructure() {
// fill the array with ascending integer values
for (int i = 0; i < SIZE; i++) {
arrayOfInts[i] = i;
}
}
public void printEven() {
// Print out values of even indices of the array
DataStructureIterator iterator = this.new EvenIterator();
while (iterator.hasNext()) {
System.out.print(iterator.next() + " ");
}
System.out.println();
}
interface DataStructureIterator extends java.util.Iterator<Integer> { }
// Inner class implements the DataStructureIterator interface,
// which extends the Iterator<Integer> interface
private class EvenIterator implements DataStructureIterator {
// Start stepping through the array from the beginning
private int nextIndex = 0;
public boolean hasNext() {
// Check if the current element is the last in the array
return (nextIndex <= SIZE - 1);
}
public Integer next() {
// Record a value of an even index of the array
Integer retValue = Integer.valueOf(arrayOfInts[nextIndex]);
// Get the next even element
nextIndex += 2;
return retValue;
}
public void setNextIndex(int i){
nextIndex=i;
}
}
public void print(DataStructureIterator iterator) {
// Print out values of odd indices of the array
//iterator = this.new EvenIterator();
iterator.setNextIndex(1);//**This line giving me compiler error that setNextIndex is undefined for type DataStructure.DataStructureIterator **
while (iterator.hasNext()) {
System.out.print(iterator.next() + " ");
}
System.out.println();
}
public EvenIterator createNewObject(){
return this.new EvenIterator();
}
public static void main(String s[]) {
// Fill the array with integer values and print out only
// values of even indices
DataStructure ds = new DataStructure();
System.out.println("Even Index");
ds.printEven();
System.out.println("Odd Index");
ds.print(ds.createNewObject());
}
}
I am passing a EvenIterator object to the method print(DataStructureIterator), as far as I know a iterator can refer to a EvenIterator object(since DataStructureIterator is a implemented by EvenIterator), though hasNext() and setNextIndex(int) are in the same class the reference iterator is able to access only hasNext.
How can I fix this bug?

Even though you are passing EvenIterator to the method print(DataStructureIterator), it is silently getting casted into DataStructureIterator. So if the setNextIndex(int) method is not declared in DataStructureIterator, you will not be able to access it.

The print method know its parameter is a DataStructureIterator. Is the method setNextIndex declared in that interface? If not, you must add it.

Related

How would I create a method that stores the parameter value in an array at the index of the position variable, then adds 1 to the position variable

I have an assignment to create an array class where there are 2 constructors where each constructor sets a different size for the array.
The array is already an instance variable along with another instance variable to keep track of the current position in the array.
I have to create a method called add with an integer parameter that will store the parameter value in the array at the index of the position variable, then add 1 to the position variable. If the incremented position variable is outside the bounds of the array, the method calls the addspace method.
The addspace method creates a new array 25% larger than the instance variable array, copies all the values of the instance array to the new array, and assigns the new array to the instance variable.
I also need a method called size that will return the value in the position variable and a method called get that with 1 parameter(an index), the method returns the value at the parameter index.
The last thing I need is a print method that uses a for loop to print the values in the array.
So far this is what I have
public class ArrayClass
{
private int array[];
private int x=0;
public ArrayClass()
{
this.array= new int[10];
add(1);
getThat(0);
print();
}
public ArrayClass(int y)
{
this.array= new int[y];
add(2);
getThat(0);
print();
}
public void add(int a)
{
array[x]=a;
x++;
if(x>array.length)
addspace();
}
public void addspace()
{
double d=array.length+(array.length*0.25);
int v=(int)d;
int newArray[]= new int[v];
for(int i=0; i<array.length; i++)
{
newArray[i]=array[i];
System.out.println(newArray[i]);
}
}
public int size()
{
return x;
}
public int getThat(int index)
{
return array[index];
}
public void print()
{
for(int i=0; i<array.length; i++)
System.out.println(array[i]+" ");
}
public static void main(String[] args)
{
new ArrayClass();
new ArrayClass(5);
}
}
I know the title only asks for help with the first method but if someone would be kind enough to help with the other methods and the reason why my code won't run and print what I want it to that would be much appreciated.
Use the ArrayClass for only for declaring your functionality.Call add method as obj.add(number) until and unless you need to add something inside ArrayClass constructor itself.
Modified these things as per my understanding
In your add method you are assigning the value first and then adding space if the array is full, in this case, you are increasing the size even if it might not be needed (i.e not calling add method again).
Instead of this increase the size only when you require it.
In print function you are iterating through the whole array.Modified to-> it will iterate till the last index of value (i.e x)
package com.example;
public class ArrayClass
{
private int array[];
private int x=0;
private final int DEFAULT_SIZE=4;
public ArrayClass(){
this.array = new int[DEFAULT_SIZE];
}
public ArrayClass(int size){
this.array = new int[size];
}
public void add(int number){
//check whether array have space or not .if not then increase the space.
if(x > this.array.length-1){
addSpace();
}
array[x] =number;
x++;
}
private void addSpace(){
double newSize = array.length + array.length * 0.25;
int tempArray[] = new int[(int) newSize];
for(int i=0; i<array.length; i++){
tempArray[i]=array[i];
}
this.array = tempArray;
}
public int size()
{
return x;
}
public int getThat(int index)
{
return array[index];
}
public void print()
{
//instead of of printing the whole array Printed till last value index.
for(int i=0; i<x; i++)
System.out.println(array[i]+" ");
}
}
From the main method
ArrayClass ac1 = new ArrayClass();
ac1.add(5);
ac1.add(4);
ac1.add(5);
ac1.add(4);
ac1.add(7);
ac1.add(19);
ac1.print();
ArrayClass ac2 = new ArrayClass(5);
ac2.add(1);
//rest of your function call here

Oracle Inner Classes Example

I don't understand this line:
interface DataStructureIterator extends java.util.Iterator<Integer> { }
since there is no difference between DataStructeIterator and iterator can't we just remove this line and instead say:
private class EvenIterator implements java.util.iterator<Integer> { //code goes here}
What am I missing?
public class DataStructure {
// Create an array
private final static int SIZE = 15;
private int[] arrayOfInts = new int[SIZE];
public DataStructure() {
// fill the array with ascending integer values
for (int i = 0; i < SIZE; i++) {
arrayOfInts[i] = i;
}
}
public void printEven() {
// Print out values of even indices of the array
DataStructureIterator iterator = this.new EvenIterator();
while (iterator.hasNext()) {
System.out.print(iterator.next() + " ");
}
System.out.println();
}
interface DataStructureIterator extends java.util.Iterator<Integer> { }
// Inner class implements the DataStructureIterator interface,
// which extends the Iterator<Integer> interface
private class EvenIterator implements DataStructureIterator {
// Start stepping through the array from the beginning
private int nextIndex = 0;
public boolean hasNext() {
// Check if the current element is the last in the array
return (nextIndex <= SIZE - 1);
}
public Integer next() {
// Record a value of an even index of the array
Integer retValue = Integer.valueOf(arrayOfInts[nextIndex]);
// Get the next even element
nextIndex += 2;
return retValue;
}
}
public static void main(String s[]) {
// Fill the array with integer values and print out only
// values of even indices
DataStructure ds = new DataStructure();
ds.printEven();
}
}
Yes, you're right; for most purposes you can do away with the DataStructureIterator and use Iterator<Integer> directly.
Defining DataStructureIterator like this creates a shorthand notation for Iterator<Integer>, but it's a very poor shorthand. It's not at all like, for example, a typedef in C.
You can assign any object that implements DataStructureIterator to Iterator<Integer>, but you cannot assign all objects that implement Iterator<Integer> to DataStructureIterator.
So, although it's legal to define an empty interface like that, there is not much point to it. And it can lead to confusion.

Generic array index out of bounds

Ok , here is my problem . I'm learing to use generic classes and methods. I want to make an generic array list and method that will add/remove element by choosen index. I simply doesn't know how to do that . My example is calling an IndexOutOfBoundsException.
Any help is welcome.
Thanks it advance .
class klasa3:
public class klasa3<E> {
private java.util.ArrayList<E> list = new java.util.ArrayList<>();
public klasa3(int initSize){
}
public int getSize() {
return list.size();
}
public E peek() {
return list.get(getSize() - 1);
}
public void push(E o,int indeks) {
o = list.get(indeks);
list.add(o);
}
public E pop(int indeks) {
E o = list.get(indeks);
list.remove(indeks);
return o;
}
public boolean isEmpty() {
return list.isEmpty();
}
#Override
public String toString() {
return "stack: " + list.toString();
}
}
main class:
public class klasa2 {
public static void main(String[] args ) {
klasa3 stak2 = new klasa3(13);
stak2.push("cola",2); // problem here
stak2.pop(2);
System.out.println(stak2.getSize());
}
}
You're creating an empty ArrayList, and then trying to get the third element (element at index 2) from it within your push method. That's not going to work.
Now, you're currently ignoring your initSize parameter in your constructor. You might want something like:
// TODO: Rename the class to follow naming conventions
public klasa3(int initSize) {
for (int i = 0; i < initSize; i++) {
list.add(null);
}
}
Or provide a default element:
// TODO: Rename the class to follow naming conventions
public klasa3(int initSize, E element) {
for (int i = 0; i < initSize; i++) {
list.add(element);
}
}
This is what is happening:
In the main method you first create a new klasa3 object. Then you call push("cola", 2) on it.
The push method does: o = list.get(indeks), where indeks is 2. At this point the list is empty, so 2 is not a valid index, which causes an IndexOutOfBoundsException.
The index that you pass to the get method must be between 0 (inclusive) and the size of the list (exclusive). Since the size is 0, the index 2 is invalid.

ClassCastException when casting Object[] array to generic type array in Java

Hi I'm very new to Java and in this code, I think I'm not creating the Bag correctly in the Main? Please help thanks!
Exception in thread "main" java.lang.ClassCastException: [Ljava.lang.Object; cannot be cast to [Ljava.lang.Comparable;
at mid.Bag.(Bag.java:12)
at mid.Bag.main(Bag.java:91)
public class Bag<T extends Comparable<T>> implements Iterable<T> {
private int MAX_ITEMS = 10; // initial array size
private int size;
private T[] data;
public Bag( ) {
data = (T []) new Object[MAX_ITEMS];
size = 0;
}
public void add(T newItem) {
// check if it's full, then extend (array resizing)
if (size == data.length) {
T[ ] temp = (T [ ] ) new Object[data.length*2];
for (int i = 0; i < size; ++i)
temp[i] = data[i];
// reassign data to point to temp
data = temp;
}
// then do the assignment
data[size++] = newItem; // assign newItem in the next-available slot
}
public Iterator<T> iterator() {
return new BagIterator();
}
/***************************
* nested class BagIterator
***************************/
class BagIterator implements Iterator<T> {
// instance member
private int index;
// (0) constructor
public BagIterator() {
index = 0;
}
// (1)
public boolean hasNext() {
return (index < size); // size in the outer Bag<E>
}
// (2)
public T next() {
/*
T temp = data[index]; // save the element value
index++; // increment index
return temp;
*/
return data[index++];
}
public static void main(String[ ] args) {
Bag<String> bag1=new Bag<String>();
bag1.add("good");
bag1.add("fortune");
bag1.add("billionarie");
for (String x: bag1)
System.out.println(x);
}
Yes, you're creating an Object[] and then trying to cast it to T[], which the compiler is converting to a cast to Comparable[] (using the raw Comparable type) due to your constraint on T.
Arrays and generics don't work terribly nicely together, basically.
It would probably be simpler to make your data field just an Object[] and cast individual values where necessary.
Here:
data = (T []) new Object[MAX_ITEMS];
you are constructing an Object array and trying to cast it to T[]. But you have declared that T inherits from Comparable. So use:
data = (T []) new Comparable[MAX_ITEMS];
You can probably rewrite your constructor as well:
public Bag(Class<T> c, int s) {
// Use Array native method to create array of a type only known at run time
#SuppressWarnings("unchecked")
final T[] dataArray = (T[]) Array.newInstance(c, s);
this.data = dataArray;
}
Then you can use it like:
Bag<String> bag1 = new Bag<>(String.class,10);
That should also work, IMO. The instances of T must be comparable in any case.

How to add an Object to a Generic array using a method Java

I want to add an object to my array. I am trying to create a method so whenever it's called, it adds the generic type object. Here's my code:
public class ArrayObjects<E> implements SomeImp<E>{
private E[] list;
private int maxCapacity, currentSize;
public ArrayObjects(){
maxCapacity = 10;
array = (E[]) new Object[maxCapacity];
}
public void addObj(E obj){
array.add(obj); //Throws an error
}
}
Eclipse shows me an error though. It says "Cannot invoke add(E) on the array type E[ ]"
Does anyone know why does this happen? Do you know of an alternative of adding an object to my generic array?
Thank you!
EDIT:
When I create an instance of a class that instantiates ArrayObjects, and try to add a value to it, it doesn't do it. code:
import packageWhereArrayObjectsIs.*;
public class Test {
private ArrayObjects<Integer> list;
public Test() {
list = new ArrayObjects<Integer>();
Test();
}
private void TestOne() {
for(int i=1; i <= 10; i++)
list.addLast(i);
System.out.println("Should print 1 .. 10");
System.out.println(list);
}
}
The method add() does not exist for arrays. You must access array elements using the correct syntax []:
public void addLast(E obj) {
array[currentSize++] = obj;
}
In order for your list to print nicely, you'll want to add a toString() method to your ArrayObjects class:
public String toString() {
return Arrays.toString(array);
}
To iterate over the elements of your ArrayObjects, you can implement the Iterable interface:
public class ArrayObjects<E> implements Iterable<E>
This requires your class to have an iterator() method that returns an Iterator:
public Iterator<E> iterator() {
class It implements Iterator<E>
{
int position = -1;
public boolean hasNext() {
return position + 1 < currentSize;
}
public E next() {
return array[++position];
}
public void remove() {
throw new UnsupportedOperationException();
}
}
return new It();
}
Finally, this code shows how you can now iterate over your list using an enhanced for loop:
ArrayObjects<Integer> list = new ArrayObjects<Integer>();
for (int i = 0; i < 10; i++) list.addLast(i);
for (Integer i: list) {
System.out.println("Iterating over list! Next element is " + i);
}
You should do something like this, assuming that your actual size is 1 when you add your first element BUT the position will be 0 because it's the first position of the array.
public boolean addObj(E obj){
if(actualSize == maxCapacity){
return false;
}
array[actualSize--] = obj;
return true;
}
I changed the return value to return false if there is no positions left in the array (considering that you won't remove any object in the middle).
Why do you need an array? Why not going with a List?
public class ArrayObjects<E> implements SomeImp<E>{
private List<E> list;
private int maxCapacity;
public ArrayObjects(){
maxCapacity = 10;
list = new ArrayList<E>();
}
public boolean addObj(E obj){
if(list.size() == maxCapacity){
return false;
}
list.add(obj);
return true;
}
}
See that using a List you won't have to deal with the actualSize.
EDIT: as Smac89 points out, it makes no sense to use a list. But keep in mind you will have to find an empty position if the array is not full.

Categories