
Kann mit „Split“ eine Datei in mehrere Segmente aufgeteilt werden, wobei die Größe jedes Segments auf der Anzahl der Übereinstimmungen eines XML-Elements basiert?
Zum Beispiel für unten XML-Split, wenn Begegnungen von "<test xsi:type="update" locale="en_US">
" ist 2
<?xml version="1.0" encoding="UTF-8"?>
<testers xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
</testers>
Durch das Aufteilen der obigen XML-Datei sollten zwei Dateien erzeugt werden.
Datei1:
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
und Datei 2 enthält nur einen einzigen Eintrag:
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
Folgendes versuche ich:
split -p "<test xsi:type=\"update\" locale=\"en_US\">" test.xml segment
welches 4 Dateien ausgibt:
segmentaa:
<?xml version="1.0" encoding="UTF-8"?>
<testers xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
segmentab:
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
segmentac:
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
segmentiert:
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
</testers>
Kann split
auf die von mir vorgeschlagene Weise genutzt werden. Die Datei, die ich verarbeite, ist 40 GB groß. Ich verwende das obige Beispiel, um das Problem zu veranschaulichen, das ich zu lösen versuche.
Antwort1
Ich glaube nicht, dass das mit möglich ist split
. Sie könnten verwenden awk
:
awk '
BEGIN{
fmt="segment%02d" # 2 digits for suffix, zero padded
start="<test xsi:type=\"update\" locale=\"en_US\">"
end="</test>"
}
$0 == start, $0 == end{
if ($0 == start && ++cnt%2==1){ # for every 2nd start element...
fname=sprintf(fmt, fcnt++) # update output filename
}
print $0 > fname # print line, redirect output to fname
}
' test.xml
Dadurch werden zwei Dateien erstellt segment00
und segment01
:
$ head segment*
==> segment00 <==
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>
==> segment01 <==
<test xsi:type="update" locale="en_US">
<rval>1</rval>
</test>