我了解如何使用[clojure.data.csv]
写入CSV但是我不知道用这种特定格式编写CSV。
我要写入CSV的数据是使用[clojure.java.jdbc]
和as-arrays? true
修饰符进行数据库查询的结果,该修饰符返回[0][1]
为column names
的二维数组需要成为CSV中的headers
,然后[x][y]
将成为写入这些标头的数据,以便[1][0]
将第一个返回的行和第0列写入第一个CSV下的CSV标题。
(with-open [out-file (io/writer "out-file.csv")]
(csv/write-csv out-file
[["abc" "def"]
["ghi" "jkl"]]))
以上是写入CSV文件的示例,但我不确定如何使用查询结果并将值写入CSV。
数据如下所示:
[[header1, header2, header3]
[val1, val2, val3]
[val1, val2, val3]]
查询如下所示:
(j/query db ["$SOME_QUERY"] as-arrays? true))
有人可以帮忙吗?
编辑:更新这是我到目前为止:
(defn write-query-to-csv [query db output-filename]
(log/info (str "Executing " query " on " db))
(let [results (j/query db ["$QUERY"]
:as-arrays? true)
header (->> results
first)
data (->> results)]
(with-open [out-file (io/writer output-filename)]
(csv/write-csv out-file
(reduce conj (conj [] header) data)))
(io/file output-filename)))
标题数据是正确的,但我不确定如何填充数据变量:/
答案 0 :(得分:1)
在我看来results
是一系列序列,在let
中,您将标题序列拉出来,但不要将其从数据中删除。然后header
包含一系列标题标签,data
包含标题序列和数据序列(每行一个序列)。 reduce
行将标题序列添加回序列序列 - 现在包含两个标题序列。大多数情况都是不必要的。由于results
的格式正确无法传递给write-csv
,因此let
只需绑定results
,然后您可以传递results
而不进行任何修改write-csv
的第二个参数,如下所示:
(defn write-query-to-csv [query db output-filename]
(log/info (str "Executing " query " on " db))
(let [results (j/query db ["$QUERY"]
:as-arrays? true)]
(with-open [out-file (io/writer output-filename)]
(csv/write-csv out-file result)
(io/file output-filename)))
因此,您不需要reduce
行,但为了将来参考,将(conj [] header)
替换为(vector header)
可能会更加清晰。另外,编写整个reduce
表达式的另一种方法是(cons header data)
。这将返回与reduce
行不同的序列,但write-csv
不会关心,我认为性能应该相似。您也可以使用(into (vector header) data)
。