Java Final arraylist

use*_*198 18 java

我的问题是将arraylist宣布为final.我知道,一旦我写了最终,ArrayList list = new ArrayList();我可以添加,删除此列表中的对象,但我不能list = new ArrayList()list = list1.但是宣称arraylist的用途是什么 Private static final ArrayList list = new ArrayList();.除了我上面提到的差异之外,以下两个声明之间的区别是什么:

1. ArrayList list = new ArrayList()

2. private static final ArrayList list =  new ArrayList();
Run Code Online (Sandbox Code Playgroud)

dav*_*veb 14

你是正确的,声明list最终意味着你不能将list变量重新分配给另一个对象.

另一个问题(我认为)是

public class SomeClass {
    private static final ArrayList list = new ArrayList();
}
Run Code Online (Sandbox Code Playgroud)

VS

public class SomeClass {
    ArrayList list = new ArrayList();
}
Run Code Online (Sandbox Code Playgroud)

让我们依次拿出每个修饰符.

private仅表示此class(SomeClass)可以访问list

static表示list所有SomeClass要共享的实例只有一个变量实例.列表实例与SomeClass类相关联,而不是与每个新的SomeClass实例相关联.如果变量是非静态的,则称其为实例变量

final 如您所知,这意味着您无法将列表变量重新分配给另一个值.

在第二个声明中没有修饰符,因此变量是一个实例变量,它还获得包私有访问保护(有时称为默认访问保护).这意味着这个class(SomeClass)和同一个包中的其他类可以访问该变量.

你可以找到更多有关public,privatepackage-private这里:访问控制

你可以找到更多关于finalstatic这里:类变量


Cer*_*ber 13

只是为了"为你的工厂带来一点水",你会明白你final何时想要使你的名单公开可用但不可修改的兴趣.

在java中,可以使用Collections.unmodifiableList(modifiableList)使列表不可修改.

现在看看以下代码:

public class MyClass{
  public static List<String> MY_PUBLIC_LIST;
  static{
    ArrayList<String> tmp = new ArrayList<String>();
    tmp.add("a");
    tmp.add("b");
    tmp.add("c");
    MY_PUBLIC_LIST = tmp;
  }
}
Run Code Online (Sandbox Code Playgroud)

好吧,在任何类中,代码中的任何地方都可以执行类似的操作

MyClass.MY_PUBLIC_LIST = null;
MyClass.MY_PUBLIC_LIST = new ArrayList<String>();
MyClass.MY_PUBLIC_LIST.clear();
MyClass.MY_PUBLIC_LIST.add("1");
Run Code Online (Sandbox Code Playgroud)

final关键字添加到变量时,前两个将不被允许

public static final List<String> MY_PUBLIC_LIST;
Run Code Online (Sandbox Code Playgroud)

但是你仍然可以修改列表的内容:

MyClass.MY_PUBLIC_LIST.clear();
MyClass.MY_PUBLIC_LIST.add("1");
Run Code Online (Sandbox Code Playgroud)

通过在静态块的末尾添加Collections.unmodifiableList(modifiableList),您也可以防止这种情况:

MY_PUBLIC_LIST = Collections.unmodifiableList(tmp);
Run Code Online (Sandbox Code Playgroud)

好的,我们差不多了.只是为了确保你得到整个图片让我们保持Collections.unmodifiableList(modifiableList),但让我删除最终修饰符

public class MyClass{
  public static List<String> MY_PUBLIC_LIST;
  static{
    ArrayList<String> tmp = new ArrayList<String>();
    tmp.add("a");
    tmp.add("b");
    tmp.add("c");
    MY_PUBLIC_LIST = Collections.unmodifiableList(tmp);
  }
}
Run Code Online (Sandbox Code Playgroud)

在那种情况下你能做什么?

...

...

那么你可以在第一种情况下做你想做的任何事情(假设你先分配新的清单):

MyClass.MY_PUBLIC_LIST = null;
MyClass.MY_PUBLIC_LIST = new ArrayList<String>();
MyClass.MY_PUBLIC_LIST.clear();
MyClass.MY_PUBLIC_LIST.add("1");
Run Code Online (Sandbox Code Playgroud)


elj*_*nso 8

当你说

final ArrayList list = new ArrayList();
Run Code Online (Sandbox Code Playgroud)

这意味着变量list将始终指向同一个ArrayList对象.有两种情况可以使用它.

  1. 您希望确保在收到其值后,没有人重新分配您的list变量.这可以降低复杂性并有助于理解类/方法的语义.在这种情况下,通常使用良好的命名约定和减少方法长度会更好(类/方法已经过于复杂而不易理解).
  2. 使用内部类时,需要final在封闭范围内声明变量,以便可以在内部类中访问它们.这样,Java可以将你的final变量复制到内部类对象中(它永远不会改变它的值),并且内部类对象不需要担心外部类对象发生什么,而内部类对象是活着的并且需要访问该变量的值.

你问题的第二部分是关于它们之间的区别

ArrayList list = new ArrayList();
Run Code Online (Sandbox Code Playgroud)

private static final ArrayList list = new ArrayList();
Run Code Online (Sandbox Code Playgroud)

当然,差异在于修饰符.private表示在类外部不可见,static表示它是在类级别定义的,并且不需要存在实例,并final在上面讨论.没有修饰符意味着包私有或默认访问.


djn*_*jna 0

你说“我可以添加、删除(和查找)对象”,但是谁?

两种情况之间的不同之处在于可以从哪些代码中调用这些列表操作。

一般来说,您需要考虑声明的范围,如果减少变量的可见性,则会大大提高代码的可维护性。如果你有一个班级:

Public Class MyThing {
   public int importantValue;

   // more code
}
Run Code Online (Sandbox Code Playgroud)

应用程序中任何其他位置的任何其他代码都可以更改该重要值。相反,如果您将其设为私有并提供读取访问器:

Public Class MyThing {
   private int importantValue;

   public int getImportantValue(){
       return importantValue;
   }

   // more code
}
Run Code Online (Sandbox Code Playgroud)

您现在知道只有类本身可以更改值 - 对于大型应用程序,这大大提高了可维护性。因此,将列表声明为私有会限制代码可以看到的内容,并更改列表的内容。

static 的使用使该列表由类的所有实例共享,而不是每个实例都获取其 ovn 副本。