返回Java中的数组是否安全?
我是Java的新手,我对用Java返回数组感到困惑。 以下是我的代码:返回Java中的数组是否安全?,java,arrays,pointers,Java,Arrays,Pointers,我是Java的新手,我对用Java返回数组感到困惑。 以下是我的代码: public class Pointer{ private final int[] data; Pointer(){ data = new int[4]; data[0] = 1; data[1] = 2; data[2] = 3; data[3] = 4; } public int[] test(){
public class Pointer{
private final int[] data;
Pointer(){
data = new int[4];
data[0] = 1;
data[1] = 2;
data[2] = 3;
data[3] = 4;
}
public int[] test(){
return data;
}
public void print(){
int length = data.length;
int j;
for(j = 0; j < length; j++){
System.out.println(data[j]);
}
}
static public void main(String[] argv){
Pointer i = new Pointer();
int[] re = i.test();
i.print();
re[2] = 1;
i.print();
}
}
公共类指针{
私有最终int[]数据;
指针(){
数据=新整数[4];
数据[0]=1;
数据[1]=2;
数据[2]=3;
数据[3]=4;
}
公共int[]测试(){
返回数据;
}
公开作废印刷品(){
int length=data.length;
int j;
对于(j=0;j
我想我返回了一个int数组,而不是指向该数组的指针,因此在我写re[2]=1时不应该更改数据。如何使此指针对象不可变 数组是Java中的对象,对象是通过引用传递的(即使引用是通过值传递的) 不能按值传递数组本身 您可以做的是返回数组的副本。这样,对返回数组的更改不会影响
指针内的内部数组(如果这是您想要的行为)
首先,看看Josh Bloch的优秀著作《有效Java》中的不可变类一章。我知道这个网站看起来像是1997年制作的,但别让它打扰你。信息是好的
为了使您的类是不可变的,您不能允许对可变的私有数据使用mutator方法(即setter)或accessor(即getter)。这否定了私有性
,并创建了一个泄漏的抽象
你发现了后者的一个例子。通过getter公开的数组是可变的。这使得您的类是可变的。没有办法使数组不可变
你有选择。以下是一些:
- 在getter中,返回类中数组的副本
- 没有getter,但允许使用类似于
getValue(int-index)
的方法在给定索引处检索数组值(如果索引超出范围,则使用类似于IllegalArgumentException
的错误处理)
- 在getter中,返回由数组构造的不可变集合,如
Collections.unmodifiableList(Arrays.asList(data))代码>。有关文档,请参阅
返回数组时唯一安全的情况是数组为空。否则我们需要返回一份副本。制作副本有两种方法1)arr.clone()2)Arrays.copyOf()相关:您搜索过吗?或者,您不能在Java中返回数组,只返回对它的引用。如果要返回的数组不是原始引用,则必须复制一个数组或按照其他数组的建议执行。@Radiodef Hi,谢谢您的回答。我将数据声明为final,但这只适用于作为引用的数据,在构造函数之前,我不知道数据有多少元素。在这种情况下,如何避免数据[0]和数据[1]被更改?是否将数据声明为最终数据并不重要。在代码示例中,test()返回数据所持有的值,该值是对数组的引用。(在Java中,它们通常被称为引用,而不是指针,尽管它基本上是指针。)我看到有人发布了一个答案,显示了复制整个数组的快速方法。否则,如果不需要更改返回的数组,请转到上面的链接之一,查看如何返回不可变数组引用。
public int[] test(){
return data.clone();
}