Хорошая печать коллекций Java (toString не возвращает симпатичный вывод) - PullRequest
195 голосов
/ 27 декабря 2008

Я хочу напечатать объект Stack<Integer> так же хорошо, как это делает отладчик Eclipse (т. Е. [1,2,3...]), но печать его с помощью out = "output:" + stack не возвращает этот хороший результат.

Просто чтобы уточнить, я говорю о встроенной коллекции Java, поэтому я не могу переопределить ее toString().

Как мне получить хорошую версию стека для печати?

Ответы [ 17 ]

295 голосов
/ 27 декабря 2008

Вы можете преобразовать его в массив, а затем распечатать его с помощью Arrays.toString(Object[]):

System.out.println(Arrays.toString(stack.toArray()));
46 голосов
/ 10 марта 2015
String.join(",", yourIterable);

(Java 8)

18 голосов
/ 16 ноября 2011

Класс MapUtils, предлагаемый проектом Apache Commons, предлагает метод MapUtils.debugPrint, который прекрасно напечатает вашу карту.

15 голосов
/ 13 августа 2014

С помощью потоков и сборщиков java 8 это легко сделать:

String format(Collection<?> c) {
  String s = c.stream().map(Object::toString).collect(Collectors.joining(","));
  return String.format("[%s]", s);
}

сначала мы используем map с Object::toString для создания Collection<String>, а затем используем объединяющий коллектор для объединения каждого элемента в коллекции с , в качестве разделителя.

12 голосов
/ 28 декабря 2008

Реализация toString () в классе.

Я рекомендую Apache Commons ToStringBuilder , чтобы сделать это проще. При этом вам просто нужно написать такой метод:

public String toString() {
     return new ToStringBuilder(this).
       append("name", name).
       append("age", age).
       toString(); 
}

Чтобы получить такой вывод:

Person @ 7f54 [имя = Стивен, возраст = 29]

Существует также отражающая реализация .

10 голосов
/ 08 сентября 2010

System.out.println (Коллекция c) уже печатает любой тип коллекции в удобочитаемом формате. Только если коллекция содержит определенные пользователем объекты, вам нужно реализовать toString () в определенном пользователем классе для отображения содержимого.

9 голосов
/ 28 декабря 2008

Я согласен с приведенными выше комментариями о переопределении toString() в ваших собственных классах (и об максимально возможной автоматизации этого процесса).

Для классов, которые вы не определяли , вы можете написать класс ToStringHelper с перегруженным методом для каждого библиотечного класса, который вы хотите обработать по своему вкусу:

public class ToStringHelper {
    //... instance configuration here (e.g. punctuation, etc.)
    public toString(List m) {
        // presentation of List content to your liking
    }
    public toString(Map m) {
        // presentation of Map content to your liking
    }
    public toString(Set m) {
        // presentation of Set content to your liking
    }
    //... etc.
}

РЕДАКТИРОВАТЬ: Отвечая на комментарий xukxpvfzflbbld, вот возможная реализация для случаев, упомянутых ранее.

package com.so.demos;

import java.util.List;
import java.util.Map;
import java.util.Set;

public class ToStringHelper {

    private String separator;
    private String arrow;

    public ToStringHelper(String separator, String arrow) {
        this.separator = separator;
        this.arrow = arrow;
    }

   public String toString(List<?> l) {
        StringBuilder sb = new StringBuilder("(");
        String sep = "";
        for (Object object : l) {
            sb.append(sep).append(object.toString());
            sep = separator;
        }
        return sb.append(")").toString();
    }

    public String toString(Map<?,?> m) {
        StringBuilder sb = new StringBuilder("[");
        String sep = "";
        for (Object object : m.keySet()) {
            sb.append(sep)
              .append(object.toString())
              .append(arrow)
              .append(m.get(object).toString());
            sep = separator;
        }
        return sb.append("]").toString();
    }

    public String toString(Set<?> s) {
        StringBuilder sb = new StringBuilder("{");
        String sep = "";
        for (Object object : s) {
            sb.append(sep).append(object.toString());
            sep = separator;
        }
        return sb.append("}").toString();
    }

}

Это не полномасштабная реализация, а просто стартер.

9 голосов
/ 04 декабря 2015

Гуава выглядит как хороший вариант:

Iterables.toString(myIterable)

5 голосов
/ 21 января 2016

Вы можете использовать класс "Objects" из JAVA (который доступен с 1.7)

Collection<String> myCollection = Arrays.asList("1273","123","876","897");
Objects.toString(myCollection);

Вывод: 1273, 123, 876, 897

Другой возможностью является использование класса "MoreObjects" из Google Guave , который предоставляет множество полезных вспомогательных функций:

MoreObjects.toStringHelper(this).add("NameOfYourObject", myCollection).toString());

Выход: NameOfYourObject = [1273, 123, 876, 897]

Документы Guava

3 голосов
/ 15 декабря 2016

С Apache Commons 3 , вы хотите позвонить

StringUtils.join(myCollection, ",")
...