2009-10-30 98 views
78

我有一個類 - xClass,我要加載到xClass數組,所以我聲明:Java動態數組大小?

xClass mysclass[] = new xClass[10]; 
myclass[0] = new xClass(); 
myclass[9] = new xClass(); 

不過,我不知道我是否會需要10.我可能需要8或12或任何其他數字。直到運行時我纔會知道。 我可以隨時更改數組中元素的數量嗎? 如果是這樣,怎麼樣?

+0

我搞掂問題的格式,你可以,如果你想要的標題,只是描述。並歡迎來到stackoverflow! :D – 2009-10-30 00:05:37

回答

128

不,你不能改變一旦創建數組的大小。您必須將其分配得比您認爲需要的還要大,否則就必須重新分配需要增加的開銷。當它你就必須分配一個新的複製從舊的數據到新:

int oldItems[] = new int[10]; 
for (int i=0; i<10; i++) { 
    oldItems[i] = i+10; 
} 
int newItems[] = new int[20]; 
System.arraycopy(oldItems, 0, newItems, 0, 10); 
oldItems = newItems; 

如果在這種情況下發現自己,我會強烈建議使用Java集合來代替。特別ArrayList基本上包裹的陣列,並且負責將邏輯的陣列生長需要:

List<xClass> mysclass = new ArrayList<xClass>(); 
myclass.add(new xClass()); 
myclass.add(new xClass()); 

通常的ArrayList是優選的解決方案的陣列無論如何有幾個原因。首先,數組是可變的。如果你有一個類,這是否:

class Myclass { 
    private int items[]; 

    public int[] getItems() { return items; } 
} 
您已經創建了一個問題,因爲主叫方可以改變你的私有數據成員,從而導致各種保護性拷貝的

。與此相比,清單版本:

class Myclass { 
    private List<Integer> items; 

    public List<Integer> getItems() { return Collections.unmodifiableList(items); } 
} 
+1

我使用ArrayList而不是List,並且一切正常。 – ConductedClever 2014-08-17 18:11:12

6

您只要設定自己創建的元素你想在任何時間的數:

xClass[] mysclass = new xClass[n]; 

然後,你可以初始化一個循環的元素。我猜這是你需要的。

如果您需要在創建陣列後添加或刪除元素,那麼您將不得不使用ArrayList

1

你在哪裏聲明MyClass的[]數組爲:

xClass myclass[] = new xClass[10] 

,簡單地傳遞作爲參數,你需要XClass元素的數量。那時你知道你需要多少?通過聲明數組爲10個元素,您不會聲明10個XClass對象,您只需創建一個包含10個xClass類型元素的數組。

2

是的,包裝它並使用集合框架。

List l = new ArrayList(); 
l.add(new xClass()); 
// do stuff 
l.add(new xClass()); 

然後在必要時使用List.toArray(),或者只是遍歷所述List。

7

正如其他人所說的,您無法更改現有Java陣列的大小。

ArrayList是標準Java對動態大小數組最接近的。然而,有一些關於ArrayList(實際上是List接口)的東西不是「數組」的。例如:

  • 您不能使用[ ... ]來索引列表。您必須使用get(int)set(int, E)方法。
  • ArrayList是使用零個元素創建的。你不能簡單的用20個元素創建一個ArrayList,然後調用set(15, foo)
  • 您不能直接更改ArrayList的大小。您可以使用各種addinsertremove方法間接執行此操作。

如果你想要更類似數組的東西,你將需要設計自己的API。 (也許有人可以與現有的第三方圖書館合唱......我找不到一個有2分鐘「研究」的人使用谷歌:-))

如果你真的只需要一個像你一樣增長的數組初始化它,那麼解決方案就是這樣的。

ArrayList<T> tmp = new ArrayList<T>(); 
while (...) { 
    tmp.add(new T(...)); 
} 
// This creates a new array and copies the element of 'tmp' to it. 
T[] array = tmp.toArray(new T[tmp.size()]); 
20

在java中數組的長度是固定的。

您可以使用一個列表來保存值,並調用toArray方法,如果需要 請參見下面的示例:

import java.util.List; 
import java.util.ArrayList; 
import java.util.Random; 

public class A { 

    public static void main(String [] args) { 
     // dynamically hold the instances 
     List<xClass> list = new ArrayList<xClass>(); 

     // fill it with a random number between 0 and 100 
     int elements = new Random().nextInt(100); 
     for(int i = 0 ; i < elements ; i++) { 
      list.add(new xClass()); 
     } 

     // convert it to array 
     xClass [] array = list.toArray(new xClass[ list.size() ]); 


     System.out.println("size of array = " + array.length); 
    } 
} 
class xClass {} 
2

至於其他用戶說,你可能需要的java.util.List的實現。

如果由於某種原因,你終於需要一個數組,你可以做兩件事情:

  • 使用列表,然後將其與myList.toArray(轉換成數組)

  • 使用特定大小的數組。如果您需要更多或更少的大小,您可以使用java.util.Arrays方法修改它。

最佳的解決方案,將取決於你的問題。)

2

我建議使用向量代替。非常易於使用,並有許多預定義的實現方法。

import java.util.*; 

Vector<Integer> v=new Vector<Integer>(5,2); 

添加元素簡單地使用:

v.addElement(int); 

(5,2)前5是向量的初始大小。如果超過初始大小,矢量將增加2個位置。如果再次超過,則會再次增加2個位置等等。

+4

除非特別需要線程安全(-ish)類型,否則應該使用ArrayList而不是Vector。 – 2012-11-27 13:07:54

2

Arrays.copyOf()方法有很多選項來解決動態增加數組長度的問題。

Java API

+0

具體如下: if(i> = mysclass.length)mysclass = Arrays.copyOf(mysclass,i + 1); mysclass [i] = new MyClass(); – 2017-08-30 20:39:36

4

您可以使用ArrayList:

import java.util.ArrayList; 
import java.util.Iterator; 

...

ArrayList<String> arr = new ArrayList<String>(); 
arr.add("neo"); 
arr.add("morpheus"); 
arr.add("trinity"); 
Iterator<String> foreach = arr.iterator(); 
while (foreach.hasNext()) System.out.println(foreach.next()); 
0

這是一個很好的做法,獲得您需要存儲的數量然後初始化數組。

例如,你會詢問用戶需要多少數據存儲,然後初始化或查詢你需要多少存儲組件或參數。 如果你想要一個動態數組,你可以使用ArrayList()並使用al.add();函數來繼續添加,那麼你可以將它轉移到一個固定的數組。

//Initialize ArrayList and cast string so ArrayList accepts strings (or anything 
ArrayList<string> al = new ArrayList(); 
//add a certain amount of data 
for(int i=0;i<x;i++) 
{ 
    al.add("data "+i); 
} 

//get size of data inside 
int size = al.size(); 
//initialize String array with the size you have 
String strArray[] = new String[size]; 
//insert data from ArrayList to String array 
for(int i=0;i<size;i++) 
{ 
    strArray[i] = al.get(i); 
} 

這樣做是多餘的,但只是向你展示的想法,ArrayList可容納不像其他基本數據類型的對象,而且非常易於操縱,從中間消除任何易爲好,具有完全dynamic.same ListStack

0

Java數組大小是固定的,您不能像在C++中那樣創建動態數組。

0

我不知道您是否可以在運行時更改大小,但是您可以在運行時分配大小。嘗試使用此代碼:

class MyClass { 
    void myFunction() { 
     Scanner s = new Scanner (System.in); 
     int myArray []; 
     int x; 

     System.out.print ("Enter the size of the array: "); 
     x = s.nextInt(); 

     myArray = new int[x]; 
    } 
} 

這會將您的數組大小指定爲在運行時輸入到x中的數組大小。

0

這是一個不使用ArrayList的方法。用戶指定大小,並且可以爲遞歸添加一個do-while循環。

import java.util.Scanner; 
    public class Dynamic { 
     public static Scanner value; 
     public static void main(String[]args){ 
      value=new Scanner(System.in); 
      System.out.println("Enter the number of tests to calculate average\n"); 
      int limit=value.nextInt(); 
      int index=0; 
      int [] marks=new int[limit]; 
      float sum,ave; 
      sum=0;  
      while(index<limit) 
      { 
       int test=index+1; 
       System.out.println("Enter the marks on test " +test); 
       marks[index]=value.nextInt(); 
       sum+=marks[index]; 
       index++; 
      } 
      ave=sum/limit; 
      System.out.println("The average is: " + ave); 
     } 
    } 
0

在Java數組的大小總是固定的長度但是有辦法在其中您可以動態增加數組的大小在運行時本身

這是最「拿來主義」,以及優選的方法來做到IT-

int temp[]=new int[stck.length+1]; 
    for(int i=0;i<stck.length;i++)temp[i]=stck[i]; 
    stck=temp; 

在上面的代碼我們正在初始化一個新的臨時[]數組,並且進一步使用for循環與原始陣列即的內容初始化臨時的內容。 STCK []。然後再將它複製回原來的,給我們一個新的SIZE新陣列。

無疑它產生一個CPU開銷由於反覆使用用於循環重新初始化一個數組。但是你仍然可以在你的代碼中使用和實現它。 如果您希望將數據動態存儲在內存中,則可以使用「鏈接列表」而不是數組。

這裏有一個實時例如基於動態堆棧提高機到數組的大小在運行時

文件名:DStack.java

public class DStack { 
private int stck[]; 
int tos; 

void Init_Stck(int size) { 
    stck=new int[size]; 
    tos=-1; 
} 
int Change_Stck(int size){ 
    return stck[size]; 
} 

public void push(int item){ 
    if(tos==stck.length-1){ 
     int temp[]=new int[stck.length+1]; 
     for(int i=0;i<stck.length;i++)temp[i]=stck[i]; 
     stck=temp; 
     stck[++tos]=item; 
    } 
    else 
     stck[++tos]=item; 
} 
public int pop(){ 
    if(tos<0){ 
     System.out.println("Stack Underflow"); 
     return 0; 
    } 
    else return stck[tos--]; 
} 

public void display(){ 
    for(int x=0;x<stck.length;x++){ 
     System.out.print(stck[x]+" "); 
    } 
    System.out.println(); 
} 

} 

文件名:Exec.java
(與主類)

import java.util.*; 
public class Exec { 

private static Scanner in; 

public static void main(String[] args) { 
    in = new Scanner(System.in); 
    int option,item,i=1; 
    DStack obj=new DStack(); 
    obj.Init_Stck(1); 
    do{ 
     System.out.println(); 
     System.out.println("--MENU--"); 
     System.out.println("1. Push a Value in The Stack"); 
     System.out.println("2. Pop a Value from the Stack"); 
     System.out.println("3. Display Stack"); 
     System.out.println("4. Exit"); 
     option=in.nextInt(); 
     switch(option){ 
     case 1: 
      System.out.println("Enter the Value to be Pushed"); 
      item=in.nextInt(); 
      obj.push(item); 
      break; 
     case 2: 
      System.out.println("Popped Item: "+obj.pop()); 
      obj.Change_Stck(obj.tos); 
      break; 
     case 3: 
      System.out.println("Displaying..."); 
      obj.display(); 
      break; 
     case 4: 
      System.out.println("Exiting..."); 
      i=0; 
      break; 
     default: 
      System.out.println("Enter a Valid Value"); 

     } 
    }while(i==1); 

} 

} 

希望這可以解決您的查詢。

0

是的,我們可以這樣做。

import java.util.Scanner; 

public class Collection_Basic { 

    private static Scanner sc; 

    public static void main(String[] args) { 

     Object[] obj=new Object[4]; 
     sc = new Scanner(System.in); 


     //Storing element 
     System.out.println("enter your element"); 
     for(int i=0;i<4;i++){ 
      obj[i]=sc.nextInt(); 
     } 

     /* 
     * here, size reaches with its maximum capacity so u can not store more element, 
     * 
     * for storing more element we have to create new array Object with required size 
     */ 

     Object[] tempObj=new Object[10]; 

     //copying old array to new Array 

     int oldArraySize=obj.length; 
     int i=0; 
     for(;i<oldArraySize;i++){ 

      tempObj[i]=obj[i]; 
     } 

     /* 
     * storing new element to the end of new Array objebt 
     */ 
     tempObj[i]=90; 

     //assigning new array Object refeence to the old one 

     obj=tempObj; 

     for(int j=0;j<obj.length;j++){ 
      System.out.println("obj["+j+"] -"+obj[j]); 
     } 
    } 


} 
0

由於ArrayList中花費太多的內存,當我需要原始類型的數組,我更喜歡使用IntStream.builder()創建int數組(您也可以使用LongStream和DoubleStream建設者)。

例子:

Builder builder = IntStream.builder(); 
int arraySize = new Random().nextInt(); 
for(int i = 0; i<arraySize; i++) { 
    builder.add(i); 
} 
int[] array = builder.build().toArray(); 

注:可用,因爲Java的8