Java Değişken dizi uzunluğu

Java projemi derlerken sorun yaşıyorum çünkü dizi uzunluğu tamsayısı (değişkendir) Object dizimde doğru bir şekilde kullanılmıyor.

import java.util.Arrays;

public class ObjectList {
    private int N;
    private Object[] fractionList = new Object[N];

    public ObjectList(int n){
        this.N = n;
    }

    public int capacity(){
        return this.N;
    }

    public void setN(int n){
    this.N = n;
    }

    public String toString(){
        return Arrays.toString(fractionList);
    }
}

public class FractionDriver {
    public static void main(String[] args){

   //creates the object list, sets N to 4
    ObjectList list = new ObjectList(4);

    System.out.println("The Objectlist has " + list.capacity() + " lines");

   //prints the array
    System.out.println(list.toString());
    }
}

derleyici çıktı budur:

The ObjectList has 4 lines
[]

Bu nedenle, dizime herhangi bir nesne ekleyemiyorum. Derleyici bir ArrayIndexOutOfBoundsException: 0 atar ve dizide hiçbir öğe olmadığını söyler.

Eğer nesne dizisi örneği değişkeninde N'yi değiştirmeyi seçersem, şöyle olur:

private Object[] fractionList = new Object[4];

Derleyici mutludur ve dizi uzunluğunu 4'e ayarlar.

Neyi yanlış yapıyorum?

2
mesaj derleyiciden gelmiyor. bu, programınızın çıktısıdır.
katma yazar Joshua, kaynak
mesaj derleyiciden gelmiyor. bu, programınızın çıktısıdır.
katma yazar Joshua, kaynak
Bir cevabı kabul edildi olarak işaretlemeyi ya da hala yardıma ihtiyaç duyuyorsanız cevabın yorumlarında açıklamayı istediğinizi unutmayınız @ nisoramen.
katma yazar Mathias Bader, kaynak
Bir cevabı kabul edildi olarak işaretlemeyi ya da hala yardıma ihtiyaç duyuyorsanız cevabın yorumlarında açıklamayı istediğinizi unutmayınız @ nisoramen.
katma yazar Mathias Bader, kaynak

8 cevap

Dizi örneğini yapıcınızda, uzunluk zaten biliniyorsa oluşturabilirsiniz:

private Object[] fractionList;

public ObjectList(int n){
    this.N = n;
    this.fractionList = new Object[n];
}

Ancak, N değerini değiştirdiğinizde diziyi de yeniden oluşturmak isteyebilirsiniz:

public void setN(int n){
    this.N = n;
   //consider copying data from the old array to the new array
    this.fractionList = new Object[n];
}
4
katma
@Beri evet, kodun içindeki bir yorumdan bahsettim. Gerçi setN'nin gerekli mantığına bağlı. Elbette, yeni dizinin eski dizinin öğelerine sığmayacak kadar küçük olduğu durumu da ele almalısınız.
katma yazar Eran, kaynak
SetN yönteminde sadece yeniden yaratmamalıyız, bur da mevcut elemanları yeni Dizi'ye klonlamayı da ele aldık, ama bu sadece küçük bir gelişme :)
katma yazar Beri, kaynak

Dizi örneğini yapıcınızda, uzunluk zaten biliniyorsa oluşturabilirsiniz:

private Object[] fractionList;

public ObjectList(int n){
    this.N = n;
    this.fractionList = new Object[n];
}

Ancak, N değerini değiştirdiğinizde diziyi de yeniden oluşturmak isteyebilirsiniz:

public void setN(int n){
    this.N = n;
   //consider copying data from the old array to the new array
    this.fractionList = new Object[n];
}
4
katma
@Beri evet, kodun içindeki bir yorumdan bahsettim. Gerçi setN'nin gerekli mantığına bağlı. Elbette, yeni dizinin eski dizinin öğelerine sığmayacak kadar küçük olduğu durumu da ele almalısınız.
katma yazar Eran, kaynak
SetN yönteminde sadece yeniden yaratmamalıyız, bur da mevcut elemanları yeni Dizi'ye klonlamayı da ele aldık, ama bu sadece küçük bir gelişme :)
katma yazar Beri, kaynak

Sorun şu ki çizgi

private Object[] fractionList = new Object[N];

Yapıcınızdan önce yürütülür. Başlatma sırası her zaman aşağıdaki gibidir:

  1. Bir üst sınıf varsa - önce onu başlat
  2. Statik değişken bildirimi ve görünüm sırasına göre statik başlatıcılar
  3. Görünüm sırasına göre örnek değişken bildirimi ve örnek başlatıcılar
  4. Yapıcı.

Yapıcınızdaki (4) kodun dizi uzunluğunu ayarlamasını istediniz, ancak dizi zaten örnek değişkeninizde (3) oluşturuldu.

Aşağıdakileri tavsiye ederim:

public class ObjectList {
    private int N;
    private Object[] fractionList;

    public ObjectList(int n){
        fractionList = new Object[n];
        this.N = n;
    }

    public int capacity(){
        return this.N;
    }

    public void setN(int n){
       //might want to copy content from old array to new one here
        fractionList = new Object[n];
        this.N = n;
    }

    public String toString(){
        return Arrays.toString(fractionList);
    }
}

Java Fasulyesi'ne uymak istiyorsanız, capac() yöntemini getCapacity() olarak yeniden adlandırmanızı da tavsiye ederim.

2
katma

Sorun şu ki çizgi

private Object[] fractionList = new Object[N];

Yapıcınızdan önce yürütülür. Başlatma sırası her zaman aşağıdaki gibidir:

  1. Bir üst sınıf varsa - önce onu başlat
  2. Statik değişken bildirimi ve görünüm sırasına göre statik başlatıcılar
  3. Görünüm sırasına göre örnek değişken bildirimi ve örnek başlatıcılar
  4. Yapıcı.

Yapıcınızdaki (4) kodun dizi uzunluğunu ayarlamasını istediniz, ancak dizi zaten örnek değişkeninizde (3) oluşturuldu.

Aşağıdakileri tavsiye ederim:

public class ObjectList {
    private int N;
    private Object[] fractionList;

    public ObjectList(int n){
        fractionList = new Object[n];
        this.N = n;
    }

    public int capacity(){
        return this.N;
    }

    public void setN(int n){
       //might want to copy content from old array to new one here
        fractionList = new Object[n];
        this.N = n;
    }

    public String toString(){
        return Arrays.toString(fractionList);
    }
}

Java Fasulyesi'ne uymak istiyorsanız, capac() yöntemini getCapacity() olarak yeniden adlandırmanızı da tavsiye ederim.

2
katma

İlk önce bu bir derleme hatası değildir. Program iyi derliyor. Buradaki sorun, fractionList dizisinin önce başlatılmasından dolayı, N değişkeninin ayarlandığı yerde yapıcının gövdesi çağrılır.

İlklendirmeyi yapıcıya taşıyabilirsiniz:

private Object[] fractionList;


public ObjectList(int n) {
    this.N = n;
    fractionList = new Object[N];
}
1
katma

İlk önce bu bir derleme hatası değildir. Program iyi derliyor. Buradaki sorun, fractionList dizisinin önce başlatılmasından dolayı, N değişkeninin ayarlandığı yerde yapıcının gövdesi çağrılır.

İlklendirmeyi yapıcıya taşıyabilirsiniz:

private Object[] fractionList;


public ObjectList(int n) {
    this.N = n;
    fractionList = new Object[N];
}
1
katma

iyi ... basit bir deyişle, Nesne [] fractionList başlatıldığında, N alanının değeri "görünmez" olur, çünkü değeri this.N = n; , derleme zamanı sabiti olan 4 numaralı değişmezden farklı olarak çağrılır.

Diziyi başlatmak için yapıcıya N parametresini iletebilirsiniz. Gibi bir şey:

public ObjectList(int n){
    this.fractionList = new Object[n];
}
0
katma

iyi ... basit bir deyişle, Nesne [] fractionList başlatıldığında, N alanının değeri "görünmez" olur, çünkü değeri this.N = n; , derleme zamanı sabiti olan 4 numaralı değişmezden farklı olarak çağrılır.

Diziyi başlatmak için yapıcıya N parametresini iletebilirsiniz. Gibi bir şey:

public ObjectList(int n){
    this.fractionList = new Object[n];
}
0
katma