Java Clojure:解析XML,首先删除首尾行
我今天带着一个我无法解决的问题来 上下文 我有一个包含此类输入的目录:Java Clojure:解析XML,首先删除首尾行,java,clojure,text-processing,Java,Clojure,Text Processing,我今天带着一个我无法解决的问题来 上下文 我有一个包含此类输入的目录: <catalogue> <produit> <nom>mince</nom> <sku>25</sku> <criterias> <criteria>65</criteria> <criteria>25</criteria> </
<catalogue>
<produit>
<nom>mince</nom>
<sku>25</sku>
<criterias>
<criteria>65</criteria>
<criteria>25</criteria>
</criterias>
</produit>
<produit>
<nom>gros</nom>
<sku>56</sku>
<criterias>
<criteria>35</criteria>
<criteria>8</criteria>
</criterias>
</produit>
</catalogue>
但是,正如您所看到的——也许我遗漏了一些东西——但是除了将所有内容作为STR进行slurp之外,我看不到从这个库解析XML的其他方法。问题是我有700MB的数据
所以我想到了更好的办法
1) 首先删除“目录”行
用绞肉机绞
25
65
25
格罗斯
56
35
8.
因此,我实际上有N个XML“文件”,对应于N个产品
2) 像这样逐行写记录
{:sku 25…}
问题
我认为第一步是可以的(我没有看到文件的尾部,头是可以的)
(defn remove-lines [input nskip]
(let [path (->> (decompose-filepath input)
(last)
(str "qsdqsdqsdqsd."))]
(with-open [rdr (io/reader input)]
(with-open [wrt (io/writer path)]
(loop [n nskip]
(let [line (.readLine rdr)]
(cond (nil? line)
nil
(and (not (nil? line)) (not (empty? (re-find #"<\\catalogue>.*" line))))
nil
:else
(cond (pos? n)
(recur (dec n))
:else
(do (doto wrt (.write line) (.newLine))
(recur n))))))))
(io/delete-file input)
(rename-file path input)))
(定义删除行[输入nskip]
(让[path(->>(分解文件路径输入)
(最后)
(str“qsdqsdqsdqsdqsd.”)
(打开[rdr(io/读卡器输入)]
(打开[wrt(io/writer路径)]
(循环[n nskip]
(让[line(.readLine rdr)]
(条件(零线)
无
(和(非(零行))(非(空)(重新查找#“*”行)))
无
:其他
(状态(位置n)
(重现(第n次12月))
:其他
(do(doto wrt(.write line)(.newLine))
(再次出现n(()()()())))
(io/删除文件输入)
(重命名文件路径输入)))
现在我想做第二步,但我不知道怎么做。我可以为1个产品这样做,但我不知道如何在保存位置的文件中添加一些内容
XML解析没有问题,所以假设我只希望这样的行作为输出(为了可见性,我删除了换行):
“mince256525”
i、 e.阅读内容,直到达到目的为止,阅读文章,写下它,然后跳转到下一篇文章
我需要其他Java类吗?如果Java代码更好,我可以使用它
或者我可能错过了clojure.data.xml
库中的某些内容
谢谢这有点幼稚,它是Java代码,但很容易移植到Clojure。因为我不需要它,所以我没有试过 包文件
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class CatalogReader {
public static void processFile (String input, String output) throws FileNotFoundException {
try {
// File input
FileInputStream fstream = new FileInputStream(input);
DataInputStream in = new DataInputStream(fstream);
BufferedReader br = new BufferedReader (new InputStreamReader(in));
//File output
File out = new File(output);
FileOutputStream fos = new FileOutputStream(out);
BufferedWriter bw = new BufferedWriter (new OutputStreamWriter(fos));
String line;
String product = "";
Pattern pat = Pattern.compile("</catalogue>");
Matcher mat;
while ((line = br.readLine()) != null) {
mat = pat.matcher(line);
while (!mat.find()) {
product.concat(line);
}
bw.write(product);
bw.newLine()
product = "";
}
br.close();
bw.close();
}
catch (IOException e) { System.err.println("Error: " + e.getMessage());}
}
}
导入java.io.BufferedReader;
导入java.io.BufferedWriter;
导入java.io.DataInputStream;
导入java.io.File;
导入java.io.FileInputStream;
导入java.io.FileNotFoundException;
导入java.io.FileOutputStream;
导入java.io.IOException;
导入java.io.InputStreamReader;
导入java.io.OutputStreamWriter;
导入java.util.regex.Matcher;
导入java.util.regex.Pattern;
公共类编目器{
公共静态void processFile(字符串输入、字符串输出)引发FileNotFoundException{
试一试{
//文件输入
FileInputStream fstream=新的FileInputStream(输入);
DataInputStream in=新的DataInputStream(fstream);
BufferedReader br=新的BufferedReader(新的InputStreamReader(in));
//文件输出
文件输出=新文件(输出);
FileOutputStream fos=新的FileOutputStream(输出);
BufferedWriter bw=新的BufferedWriter(新的OutputStreamWriter(fos));
弦线;
字符串乘积=”;
Pattern pat=Pattern.compile(“”);
火柴垫;
而((line=br.readLine())!=null){
mat=匹配器(线);
而(!mat.find()){
产品线;
}
写(产品);
bw.newLine()
产品=”;
}
br.close();
bw.close();
}
catch(IOException e){System.err.println(“错误:+e.getMessage());}
}
}
(clojure.data.xml/parse(io/输入流(io/文件“catalog-fr.xml”))应该足够了。clojure.data.xml/parse返回元素recordsThanks的惰性树,事实上我的write函数有问题,但parse更好。我写了一个java函数来实现我想要的,但最终它是无用的!现在一切都好了。@JosephYourine如果你已经解决了这个问题,请不要忘记自己回答这个问题(或者干脆删除它)。
(defn remove-lines [input nskip]
(let [path (->> (decompose-filepath input)
(last)
(str "qsdqsdqsdqsd."))]
(with-open [rdr (io/reader input)]
(with-open [wrt (io/writer path)]
(loop [n nskip]
(let [line (.readLine rdr)]
(cond (nil? line)
nil
(and (not (nil? line)) (not (empty? (re-find #"<\\catalogue>.*" line))))
nil
:else
(cond (pos? n)
(recur (dec n))
:else
(do (doto wrt (.write line) (.newLine))
(recur n))))))))
(io/delete-file input)
(rename-file path input)))
"<produit><nom>mince</nom><sku>25</sku><criterias><criteria>65</criteria><criteria>25</criteria></criterias></produit>"
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class CatalogReader {
public static void processFile (String input, String output) throws FileNotFoundException {
try {
// File input
FileInputStream fstream = new FileInputStream(input);
DataInputStream in = new DataInputStream(fstream);
BufferedReader br = new BufferedReader (new InputStreamReader(in));
//File output
File out = new File(output);
FileOutputStream fos = new FileOutputStream(out);
BufferedWriter bw = new BufferedWriter (new OutputStreamWriter(fos));
String line;
String product = "";
Pattern pat = Pattern.compile("</catalogue>");
Matcher mat;
while ((line = br.readLine()) != null) {
mat = pat.matcher(line);
while (!mat.find()) {
product.concat(line);
}
bw.write(product);
bw.newLine()
product = "";
}
br.close();
bw.close();
}
catch (IOException e) { System.err.println("Error: " + e.getMessage());}
}
}