Подтвердить что ты не робот

Печать примитивных массивов в Clojure

Я на REPL, и я создаю массив java:

=> (def arr (double-array [1 2 3]))

Конечно, если я хочу посмотреть на мой arr, я получаю:

=> arr
#<double[] [[email protected]>

Есть ли что-нибудь, что я могу сделать, чтобы массивы java-примитивов печатались как clojure persistentVector s?

=> arr
[1.0 2.0 3.0]

Я знаю, что мог бы переносить свои массивы в какую-то приятную функцию печати (это то, что я сейчас делаю), но это боль в случаях, например, когда векторы являются частью карты:

=> my-map
{"1" #<double[] [[email protected]>, "2" #<double[] [[email protected]>}
4b9b3361

Ответ 1

Будет ли что-то простое, как это сделать?

user=> (seq arr)
(1.0 2.0 3.0)

Если это только для REPL, то, возможно, техническая семантика не имеет значения.

Обновление

Оказывается, что довольно печатная (pprint) отлично работает с вашей картой векторов:

user=> (def my-map {"1" (double-array [1 2 3])
                    "2" (double-array [1 2 3])})
#'user/my-map
user=> (pprint my-map)
{"1" [1.0, 2.0, 3.0], "2" [1.0, 2.0, 3.0]}

Окончательное обновление: из связанного обсуждения групп Google в комментариях

Вопросник нашел ответ, который ему понравился в обсуждении, перефразируемом ниже:

> Есть ли способ сделать по умолчанию символ Clojure по-умолчанию?

Попробуйте:

(clojure.main/repl :print pprint)

> Спасибо! Это именно то, что мне нужно.

Ответ 2

Функция str просто вызывает .toString объекта Java, что не слишком удобно для массивов. Чтобы получить хорошее представление (как утверждают другие), можно вызвать (java.util.Arrays/toString arr).

Однако как это можно реализовать прозрачно в обычном clojure println и str-коде? Можем ли мы реализовать прокси-сервер в Array и заменить метод .toString? Или нам нужно реализовать новый протокол str2, используя str для всех, кроме класса Array?

Мое предположение, что proxied arr будет лучшим вариантом, поскольку это будет работать с другим кодом, который вызывает str на нем, даже если он был вызван из другого пространства имен. Не знаю, как реализовать прокси-сервер в Array, хотя:)

Ответ 3

Всегда существует решение Java-взаимодействия:

(java.util.Arrays/toString arr)

Итак, у вас будет

(map #(java.util.Arrays/toString (val %)) my-map)