У меня есть HTML представлены в странной форме (это гораздо проще работать, чем обычная гнездовые один):алгоритм для преобразования из одного HTML представления других
[{:text "5d" :em true :strong true}
{:text "xx" :em true}
{:text "damn" :em true :strong true}
{:text "c6"}
{:text "qwe" :em true}
{:text "asd"}
{:text "qqq" :em true :strong true}]
Мне нужно, чтобы преобразовать его к икота, как один:
[[:em
[:strong "5d"]
"xx"
[:strong "damn"]]
"c6"
[:em "qwe"]
"asd"
[:strong [:em "qqq"]]]
лучшее внедрение я придумал это:
(defn wrap-tags [states nodes]
(if (seq states)
(reduce
(fn [nodes state]
[(into [state] nodes)])
nodes states)
nodes))
(defn p->tags
([data]
(p->tags data #{} [] []))
([[node & rest] state waiting result]
(let [new-state (set (keys (dissoc node :text)))
closed (clojure.set/difference state new-state)
waiting (conj (wrap-tags closed waiting) (:text node))
result (if-not (seq new-state)
(into result waiting)
result)
waiting (if-not (seq new-state) [] waiting)]
(if (seq rest)
(p->tags rest new-state waiting result)
(if (seq waiting)
(into result (wrap-tags new-state waiting))
result)))))
Он не работает должным образом, хотя он не обрабатывает случай, когда появляется сильное (он не знает, сколько «ожидающих» узлов он должен обернуть и обернуть их все), но у меня нет идей, как отслеживать это). Это выглядит немного уродливо для меня, но это менее раздражает. :) Что он возвращает для моего дела прямо сейчас:
[[:em
[:strong
[:strong "5d"]
"xx"
"damn"]]
"c6"
[:em "qwe"]
"asd"
[:em [:strong "qqq"]]]
Мне бы хотелось услышать какие-либо идеи по улучшению моего кода.
Кажется, вам нужна обратная сторона алгоритма сглаживания дерева, поскольку данные, которые у вас есть, являются результатом сплющивания дерева икоты. – Ankur
Да, что-то в этом роде, я просто не мог придумать хороший способ сделать это. –
почему первый '{: text" 5d ": em true: strong true}' приводит к '[: em [: strong]]', last one '{: text" qqq ": em true: strong true} => [ : strong [: em]] ' – edbond