Dlaczego metoda toString () działa inaczej między tablicą a obiektem ArrayList w Javie

    String[] array = {"a","c","b"};
    ArrayList<String> list = new ArrayList<String>();
    list.add("a");
    list.add("b");
    list.add("c");
    System.out.println(array);
    System.out.println(list);

Dla list [a, b, c] jest wyjściem, podczas gdy dla array jakiś adres jest wyjściem. Kiedy chcemy wypisać array wartości, możemy użyć Arrays.toString(array);, który działa tak samo jak list.

Zastanawiam się tylko, dlaczego nie możemy wywołać toString() bezpośrednio na array, aby uzyskać wartości. Czy nie jest to bardziej intuicyjne i wygodne? Jakie efekty dają różne zabiegi na Array i ArrayList?

Author: Terry Li, 2012-12-08

6 answers

Główna różnica między tablicami a arraylist polega na tym, że arraylist jest klasą napisaną w języku Java i ma własną implementację (w tym decyzję o nadpisaniu toString), podczas gdy tablice są częścią samej specyfikacji języka. W szczególności JLS 10.7 stwierdza:

Członkowie typu array są następujące:

  • publiczna końcowa długość pola
  • publiczny klon metody, który nadpisuje metodę ta sama nazwa w obiekcie klasy i nie rzuca zaznaczonych WYJĄTKÓW.
  • wszystkie elementy dziedziczone z obiektu klasy; jedyną metodą obiektu, która nie jest dziedziczona, jest jego metoda klonowania.

Innymi słowy, specyfikacja języka zapobiega nadpisywaniu metody toString tablicy i dlatego używa domyślnej implementacji zdefiniowanej w Object, która wypisuje nazwę klasy i hashcode.

Dlaczego ta decyzja została podjęta jest pytanie, które powinno prawdopodobnie zostanie poproszony o projektantów języka...

 13
Author: assylias,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-12-08 18:21:09

Zastanawiam się tylko, dlaczego nie możemy wywołać ToString() bezpośrednio na tablicy, aby uzyskać wartości.

W rzeczywistości toString metoda jest wywołana na obiekcie array. Ale ponieważ typ tablicy nie nadpisuje metody toString z klasy Object, więc wywołana jest domyślna implementacja toString, która zwraca reprezentację postaci, którą widzisz.

Reprezentacja ma postać:-

[typeOfArray@hashCode

W Twoim przypadku jest to coś w stylu:-

[Ljava.lang.String;@3e25a5

Natomiast w przypadku ArrayList instancje, wywołana jest nadpisana Metoda toString w klasie ArrayList.

 4
Author: Rohit Jain,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-12-08 18:25:41

Krótka odpowiedź jest taka, że toString jest zdefiniowany w kilku różnych miejscach, z różnymi zachowaniami.

Klasa Arrays definiuje ToString jako statyczną metodę, która ma być wywoływana jak

Arrays.toString(arr_name);

Ale Klasa Arrays dziedziczy również niestatyczną metodę toString z klasy obiektu. Tak więc wywołanie instancji wywołuje obiekt.toString, który zwraca reprezentację łańcuchową obiektu (np.: [Ljava.lang.Obiekt; @ 4e44ac6a)

Więc Macierze.toString () i MyObject.toString () wywołuje różne metody o tej samej nazwie.

Klasa ArrayList dziedziczy toString z klasy AbstractCollection, gdzie jest metodą niestatyczną, więc może być wywołana na obiekcie jak:

MyArrayList.toString();

Ponieważ jest to łańcuchowa reprezentacja kolekcji, a nie obiektu, wynikiem są wartości w formacie czytelnym, takim jak [one, two].

 1
Author: danf,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-03-08 15:37:34

Ponieważ po wydrukowaniu toString(), domyślnie wydrukuje className@HashCode.

Więc po wydrukowaniu {[3] } powyżej zostanie wydrukowane.

Ale ArrayList jest rozszerzona o klasę AbstractCollection i gdzie Metoda toString() jest nadrzędna jak poniżej

 public String toString() {
        Iterator<E> it = iterator();
        if (! it.hasNext())
            return "[]";

        StringBuilder sb = new StringBuilder();
        sb.append('[');
        for (;;) {
            E e = it.next();
            sb.append(e == this ? "(this Collection)" : e);
            if (! it.hasNext())
                return sb.append(']').toString();
            sb.append(',').append(' ');
        }
    }

Który wyświetla czytelny format obiektu ArrayList.

 0
Author: Bhavik Ambani,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-12-08 18:21:33

Jest to wywołanie metody ToString dla ArrayList. Ale w przypadku tablic takich nie można znaleźć.

 /**
 * Returns a string representation of this collection.  The string
 * representation consists of a list of the collection's elements in the
 * order they are returned by its iterator, enclosed in square brackets
 * (<tt>"[]"</tt>).  Adjacent elements are separated by the characters
 * <tt>", "</tt> (comma and space).  Elements are converted to strings as
 * by {@link String#valueOf(Object)}.
 *
 * @return a string representation of this collection
 */
public String toString() {
    Iterator<E> it = iterator();
    if (! it.hasNext())
        return "[]";

    StringBuilder sb = new StringBuilder();
    sb.append('[');
    for (;;) {
        E e = it.next();
        sb.append(e == this ? "(this Collection)" : e);
        if (! it.hasNext())
            return sb.append(']').toString();
        sb.append(',').append(' ');
    }
}
 0
Author: Suranga,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-12-08 18:23:26

Dla array metoda ToString () wypisuje adres pamięci. Ale w {[2] } klasa ta nadpisuje Object metoda toString().

ToString () implementacja ArrayList

   public String toString() {
    Iterator<E> i = iterator();
    if (! i.hasNext())
        return "[]";

    StringBuilder sb = new StringBuilder();
    sb.append('[');
    for (;;) {
        E e = i.next();
        sb.append(e == this ? "(this Collection)" : e);
        if (! i.hasNext())
        return sb.append(']').toString();
        sb.append(", ");
    }
}
 -1
Author: kannanrbk,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-12-08 18:23:23