=== 关于结束问题的评论 ====
虽然示例中的数据已本地化,但最终脚本对于拥有一组复杂 xml 文件以转换为文本数据库的任何人都非常有用,因为该过程将处理任何输入 xml,而不管其归属如何。
=== 新信息 ==== 我已经能够在初始过程中生成所有标签的列表,但是然后重新创建 tag::text 对是不可行的,因为它必须运行 1000 个 xml,生成一个唯一的排序列表,然后重新读取 xml 并开始创建文本数据集。
因此,如果给出以下内容(或任何带有唯一分隔符的文本),我可以遍历并捕获标签吗?
:;:^1^L:\Vector_Data\Administrative\Boundaries\Federal_Govt\COM_ELB_region.shp_BaseMetadata.xml^citeinfo::None^descript::None^timeperd::None^status::None^distinfo::None^dataqual::None^cntinfo::None^metainfo::None^uniqueid::None^title::COM_ELB_region.shp^origin::None^custod::Tablelands Regional Council ^jurisdic::None^;:;
(在这种情况下 ^ 是列分隔符, :: 是标签::文本分隔符)
我需要它给我一个标签列表,如 [citeinfo、timeprd、status 等],然后运行并创建另一个只有文本的数据集。
我将强调这不是本地化的,因为该解决方案将适用于任何需要解构的 xml。
=== 原始问题如下
我通过构建许多不同的 xml 样式文档创建了一个文本文件。我将 tag::text 记录在一起,因为每个文件的标签顺序略有不同。关键是原始 xml 文件的名称。
是否可以从数据中重建 excel 或“csv”,以便所有文件的列都正确排序。
谢谢,
==== 从输出中获取标签列表很困难,因为您需要逐行搜索标签,如果不重复则添加到列表中。所以我决定在解析xml时生成标签列表更容易。这很有效,但是当在 xml 中找不到有序列表中的标签时,我遇到了告诉脚本该怎么做的问题。请参阅下面的代码。
#-------------------------------------------------------------------------------
# Name: Convert xml data to csv with anzlic tagged data kept seperate
# Purpose: Also has an excel template to convert the data into standard columns
#
# Author: georgec@atgis.com.au
#
# Created: 05/03/2013
# Copyright: (c) ATGIS. georgec 2013
# Licence: Creative Commons
#-------------------------------------------------------------------------------
import os, xml, shutil, datetime
from xml.etree import ElementTree as et
from lxml import etree
SourceDIR=r'L:\Data_Admin\XML_CSV_Convertor\test_data'
#SourceDIR=os.getcwd()
rootDir=os.getcwd()
log_name='t2_'
xmllist=[]
xmltaglist=[]
x=0
def locatexml(SourceDIR,x, rootDir, xmllist, xmltaglist):
for root, dirs, files in os.walk(SourceDIR, topdown=False):
for fl in files:
currentFile=os.path.join(root, fl)
ext=fl[fl.rfind('.')+1:]
if ext=='xml':
xmllist.append(currentFile)
print currentFile
x+=1
## try:
processxmltag(currentFile,x, rootDir, xmltaglist)
## except:
## print "Issue with file: "+ currentFile
## log=open(rootDir+'\\'+log_name+'issue_xml_log.txt','a')
## log.write(str(x)+'^'+currentFile+'\n')
## log.close
print "finished"
return xmllist, x, currentFile
def processxmltag(currentFile,x, rootDir, xmltaglist):
from collections import OrderedDict
with open(currentFile) as f:
tree = etree.parse(f)
for tagn in tree.iter(tag=None):
if tagn.tag not in xmltaglist:
print tagn.tag
xmltaglist.append(tagn.tag)
else:
print 'tag exists: ' + str(tagn.tag)
return xmltaglist.sort()
def processxmlfile(xmllist, xmltaglist):
seperator='^'
for fl in xmllist:
with open(fl) as f:
tree = etree.parse(f)
if 'anzmeta' in str(tree.getroot()):
log=open(rootDir+'\\'+log_name+'anzmeta_xml_log.txt','a')
log.write(':;:'+seperator+str(x)+seperator+fl+seperator)
print xmltaglist
for xmltag in xmltaglist:
if xmltag not in tree:
print str(xmltag)+"::DoesNotExist"
log.write(str(xmltag)+"::DoesNotExist"+seperator)
for element in tree.iter(xmltag):
#print element[x]
for child in element.getchildren():
print "{0.tag}: {0.text}".format(child)
log.write("{0.tag}".format(child)+"::"+"{0.text}".format(child).replace('\n','')+seperator)
log.write('^;:;\n')
log.close
else:
print fl+" not an anzlic metadata file...logging seperately"
log=open(rootDir+'\\'+log_name+'non_anzmeta_xml_log.txt','a')
log.write(':;:'+seperator+str(x)+seperator+fl+seperator)
for xmltag in xmltaglist:
for element in tree.iter(xmltag):
#print element[x]
for child in element.getchildren():
print "{0.tag}: {0.text}".format(child)
log.write("{0.tag}".format(child)+"::"+"{0.text}".format(child).replace('\n','')+seperator)
log.write('^;:;\n')
log.close
locatexml(SourceDIR,x, rootDir,xmllist, xmltaglist) #run locate xml and process to get sorted list of all tags
processxmlfile (xmllist, xmltaglist)