2016-07-29 79 views
0

我有xml文件,需要提取所需的标签值并将结果输出到csv文件中,标签名称包含标题并低于其值。从xml文件获取标签值并使用批处理脚本将结果保存在csv文件中

到目前为止,我尝试过的获取XML标记和值,但所有结果都显示在1列而不是表格格式。

XML文件内容(部分文件内容):

<RSP> 
<HSI> 
<SN>CZ9V  </SN> 
<SP>Pro Gen8</SP> 
<UUID>C9V</UUID> 
</HSI> 
<STP>3</STP> 
<cUUID>343-11</cUUID> 
<NICS> 
<NIC> 
<PORT>1</PORT> 
<MACADDR>01:51:f2</MACADDR> 
</NIC> 
<NIC> 
<PORT>1</PORT> 
<MACADDR>00:17</MACADDR> 
</NIC> 
<NIC> 
<PORT>2</PORT> 
<MACADDR>77:28:02</MACADDR> 
</NIC> 
<NIC> 
<PORT>3</PORT> 
<MACADDR>00:04</MACADDR> 
</NIC> 
<NIC> 
<PORT>4</PORT> 
<MACADDR>00:06</MACADDR> 
</NIC> 
</NICS> 
</RSP> 

输出是从output.csv文件中获取:

SN,SP,UUID,MACADDR,cUUID 
CZ9V 
Pro Gen8 
C9V 

01:51:F2 343-11

什么我期待得到的是:

SN,SP,UUID,MACADDR,cUUID 
CZ9V,Pro Gen8,C9V,01:51:f2,343-11 

当我们在电子表格中打开output.csv时,如果需要使用过滤器选项,上述所有结果应该很容易过滤。

代码到目前为止我获得:

echo SN,SP,UUID,MACADDR,cUUID> %outFile% 
set req_tags=SN SP UUID MACADDR cUUID 
for %%a in (%inFile%) do (
for %%c in (%req_tags%) do (
set "found=" 
set search_tag=%%c 
for /f "tokens=2 delims=>< " %%b in (' type "%%a" ^|findstr /i !search_tag! ') do set found=%%b 
if defined found >> "%outFile%" echo !found! 
) 
) 

需要得到相应的下标记名称标签vlaue在output.csv文件。

+0

您建议的输出是一个固定宽度的文本文件,它与CSV完全不同。 – dbenham

+0

没问题。我不应该在这里格式化预期的输出。 – HULK

回答

0

鉴于需求有所变化,我选择发布一个新的答案,而不是编辑原来的答案。不知道是否这是做事的方式,但嘿,我尽我所能... :)

这是一个不关心XML层次结构的版本,它只是从指定元素的列表中提取标记值。但是,请注意,正如我前面所解释的,多个子元素可能属于共同的父元素(即使XML层次结构不反映它)的情况是而不是在此处理。但是,OP的要求是输出在一行上:

@echo off 
setlocal enabledelayedexpansion 
set req_tags=SN SP UUID MACADDR cUUID 
set inFile="C:\tests\xmltocsv.txt" 
set outFile="C:\tests\output.csv" 
if exist %outFile% del %outFile% 

rem set the header line 
set hLine= 
for %%a in (%req_tags%) do (
    set hLine=!hLine!,%%a 
) 
call :outputlinetocsv "%hLine%" 

rem add values to file 
set csvLine= 
for %%a in (%req_tags%) do (
    set sTag=%%a 
    for /F "tokens=2 delims=<>" %%f in ('findstr /I /L "^</!sTag!" %inFile%') do (
    set line=%%f 
    set "line=!line:*>=!" 
    set csvLine=!csvLine!,!line! 
) 
) 
call :outputlinetocsv "%csvLine%" 
goto :eof 

:outputlinetocsv 
REM remove starting comma 
set myLine=%~1 
set "myLine=!myLine:*,=!" 
echo !myLine! >> %outFile% 
goto :eof 
+0

谢谢菲利普斯。您的第二个代码按预期工作。只发布我看到的是,如果reg_tag在输入xml文件中多次出现,那么您的代码将获得两个值。像在mycase中一样,UUID在输入文件中出现两次。 – HULK

+0

是的,这就是我在我的文章中解释的:多个孩子不能这样处理。您可以编写异常来处理这些情况,但是如果您想使其具有绝对通用性,则必须使用脚本语言中的实际XML解析器,正如我在之前的某个评论中所建议的那样。 – Filipus

0

我捅了一下。你在正确的轨道上。以下代码看起来好像适用于您发布的示例数据,并且它将继续适用于您在HSI元素中添加的任何其他项目。

您需要修改的唯一的事情是CSV标题行,但你可以选择通过作为参数传递给批处理文件或硬编码这个批处理文件里面的价值观,像现在这样:

@echo off 
setlocal enabledelayedexpansion 
set inFile="C:\tests\xmltocsv.txt" 
set outFile="C:\tests\output.csv" 
if exist %outFile% del %outFile% 
set csvline= 
echo SN SP UUID > %outFile% 
(for /F "delims=" %%a in ('findstr /I /L /V "^<HSI" %inFile%') do (
    if "%%a" EQU "</HSI>" (
    echo !csvline! & set csvline= 
) ELSE (
    set line=%%a & set "line=!line:*>=!" & for /F "delims=<" %%b in ("!line!") do (IF "%%b" NEQ " " (IF "!csvline!" NEQ "" (set csvline=!csvline! %%b) ELSE (set csvline=%%b))) 
) 
)) >> %outFile% 
+0

谢谢菲利普斯,但是当我运行你的代码时,我没有在output.csv文件中获得任何值。此外,输入文件将具有标签,并且所需的标签/值将位于不同的父标签下(而不仅仅是内部的标签)。所以,我想为ex:requried_tags =“SN SP UUID ..设置一个变量。 ... etc“,并且在代码中它应该获取这些标记值,并将结果存入output.csv,第一行包含标记名称,并且低于它的相应值。对不起,我应该给出正确的input.xml文件内容,而不仅仅是一个部分。 (我现在更新了它) – HULK

+0

好的,我对代码进行了一些更改,以便定义requried_tag可以被搜索并将值发送到output.csv。它正在工作,但所有标签值都在第一列之后。不知道我现在需要做什么。有点受到任何帮助/建议的欢迎。我已经更新了最初的代码/输出结果。 – HULK

+0

我不知道我怎么知道哪些标签属于哪个项目,如果它们不存储在同一父项下。你的例子显示你在/ NICS/NIC元素下的项目与HSI元素下的项目相匹配,但大概你可能有几个NIC元素,那么你如何将它们与相应的HSI元素匹配?输入文件中是否有多个HSI元素实例?他们是否归入HSIS家长? – Filipus

相关问题