Ответ 1
Вероятно, вам нужен aget:
(aget foo "list")
aget еще не изменен, но, надеюсь, скоро будет
теперь он изменен. (aget data "o" "answer")
будет работать
У кого-нибудь есть какие-либо документы для идиоматического clojurescript для доступа к объекту javascript (возвращенный как json, по существу хэш)?
У меня есть объект JSON, возвращаемый через запрос AJAX:
{
list: [1,2,3,4,5],
blah: "vtha",
o: { answer: 42 }
}
Как получить доступ к этим полям с помощью clojurescript?
Я могу сделать:
(.-list data)
Но как это работает, когда у меня есть вложенные значения и объекты?
(.-answer (.-o data))
Вышеприведенное кажется довольно неуклюжим, особенно учитывая хороший синтаксис js: data.o.answer.
Каков идиоматический способ доступа к объектам json с clojurescript?
Примечание:
Я понял, что могу фактически ссылаться на элементы с использованием синтаксиса JS, что на самом деле весьма удобно. Таким образом, следующее будет работать правильно:
(str data.o.answer)
Вероятно, вам нужен aget:
(aget foo "list")
aget еще не изменен, но, надеюсь, скоро будет
теперь он изменен. (aget data "o" "answer")
будет работать
Во-первых, ваш предложенный синтаксис для вложенного доступа работает:
ClojureScript:cljs.user> (def data
(JSON/parse "{\"list\": \"[1,2,3,4,5]\", \"blah\": \"vtha\", \"o\": {\"answer\": \"42\"}}"))
#<[object Object]>
ClojureScript:cljs.user> (.-answer (.-o data))
"42"
Вы можете использовать макросы threading...
ClojureScript:cljs.user> (-> data (.-o) (.-answer))
"42"
Или ..
нотация
ClojureScript:cljs.user> (.. data -o -answer)
"42"
Если вы имеете дело с любым количеством данных, я бы преобразовал JSON в структуры данных clojure, а затем использовал обычные идиомы:
(let [my-json (js* "{
list: [1,2,3,4,5],
blah: \"vtha\",
o: { answer: 42 }
}")
converted (js->clj my-json)]
(get-in converted ["list" 3]) ;; => 4
(-> converted "o" "answer") ;;=> 42
)
(Примечание: не используйте js*
, если вы можете ему помочь, это не идиоматично и может исчезнуть в будущих версиях ClojureScript.)
Clojurescript имеет оператор.., который полезен для прикованных javascript-вызовов:
(.. data -o -answer) => data.o.answer => 42
(aget (.. data -list) 1) => data.list[1] => 2
Вы также можете использовать большинство операторов списка на массивах, например
(into [] (.. data -list)) ; vector [1 2 3 4]
Забудьте о aget, в основном предназначенном для массива (array get). Используйте
Подробнее