Xml 在Clojure中,如何对集合应用函数

Xml 在Clojure中,如何对集合应用函数,xml,clojure,zipper,Xml,Clojure,Zipper,我试图应用这个函数从标记集合的xml中提取一个标记的内容。基本上,我正在尝试创建一个从xml中提取内容的函数,如下所示 (defn get-events [xz] (map (juxt #(zf/xml1-> % :title zf/text) #(zf/xml1-> % :performers :performer :name zf/text) #(zf/xml1-> % :start_time zf/text) #(zf/xml

我试图应用这个函数从标记集合的xml中提取一个标记的内容。基本上,我正在尝试创建一个从xml中提取内容的函数,如下所示

(defn get-events
[xz] 
 (map (juxt 
    #(zf/xml1-> % :title zf/text) 
    #(zf/xml1-> % :performers :performer :name zf/text) 
    #(zf/xml1-> % :start_time zf/text) 
     #(zf/xml1-> % :stop_time zf/text))
 (zf/xml-> xz  :events :event)))
到目前为止,我的解决方案是这样的

(ns datamodel

(:use 
[net.cgrand.enlive-html :as en-html ])
(:require
[clojure.zip :as z] 
[clojure.xml :as xml ]
[clojure.data.zip.xml :as zf]
 [clojure.java.io :as io]
))


(def data-url "http://api.eventful.com/rest/events/search?   app_key=4H4Vff4PdrTGp3vV&keywords=music&location=Belgrade&date=Future")

(defn xz [url](z/xml-zip (xml/parse url)))

(defn xml-zipper [& tags](zf/xml-> (xz data-url) tags))

(defn func [& tags]#(zf/xml1-> (xml-zipper tags) % zf/text))

(def tags [:title :venue_name])
(map #((apply comp (reverse( func :events :event))) %) tags)
在REPL中,当我尝试将func应用于这样的标记时

(ns datamodel

(:use 
[net.cgrand.enlive-html :as en-html ])
(:require
[clojure.zip :as z] 
[clojure.xml :as xml ]
[clojure.data.zip.xml :as zf]
 [clojure.java.io :as io]
))


(def data-url "http://api.eventful.com/rest/events/search?   app_key=4H4Vff4PdrTGp3vV&keywords=music&location=Belgrade&date=Future")

(defn xz [url](z/xml-zip (xml/parse url)))

(defn xml-zipper [& tags](zf/xml-> (xz data-url) tags))

(defn func [& tags]#(zf/xml1-> (xml-zipper tags) % zf/text))

(def tags [:title :venue_name])
(map #((apply comp (reverse( func :events :event))) %) tags)

我得到一个空集合()。

def
ing
tags
时,您实际上不是在构建一个文本列表,而是调用
:title
,并将
:vention\u name
作为其参数。尝试以以下方式将
标记声明为列表或向量:

(def tags '(:title :venue_name)) ;list
(def tags [:title :venue_name]) ; vector
我建议您稍微清理一下代码,因为它似乎有很多问题:

  • clojure.data.zip.xml的双重要求
  • 函数定义中的附加括号
    xz
  • xz
    用作命名空间的别名和函数名
  • 删除括号
    func
    匿名函数
    (#(zf/xml1->(xml拉链标签)%zf/text))
    ,您同时创建并调用该
    fn
  • 希望能有帮助


    编辑

    我想我现在明白你想做什么了。以下是选择器生成器功能的工作版本:
    selector
    。请注意,参数
    标记
    可以是单个关键字,也可以是一系列关键字,在这种情况下,调用
    xml1->
    时使用
    apply

    (ns datamodel
      (:require [clojure.zip :as z] 
                [clojure.xml :as xml]
                [clojure.data.zip.xml :as zf]
                [clojure.java.io :as io]))
    
    (def data-url "http://api.eventful.com/rest/events/search?app_key=4H4Vff4PdrTGp3vV&keywords=music&location=Belgrade&date=Future")
    
    (defn parse [url]
      (z/xml-zip (xml/parse url)))
    
    (defn selector [tag]
      (if (sequential? tag)
        #(apply zf/xml1-> % (concat tag [zf/text]))
        #(zf/xml1-> % tag zf/text)))
    
    (defn get-events
      [xml & tags]
      (let [events (zf/xml-> xml :events :event)
            fs     (map selector tags)]
        (map (apply juxt fs) events)))
    
    (-> data-url 
      parse 
      (get-events :title :start_time [:performers :performer :name] :stop_time)
      first 
      prn)
    

    谢谢juan,但是现在我得到了java.lang.IllegalArgumentException:传递给以下对象的参数(0)的数目错误:@Vesna我在问题列表中添加了第4项,我认为这解决了您现在看到的错误。我已经更改了它,仍然没有运气,我想知道是否有可能创建一个函数列表,这正是我想要的