OS.Walk () Python: تمثيل XML لهيكل الدليل ، عودة
-
21-09-2019 - |
سؤال
لذلك أحاول استخدام OS.Walk () لإنشاء تمثيل XML لهيكل الدليل. يبدو أنني أحصل على طن من التكرارات. إنه يضع الدلائل بشكل صحيح داخل بعضها البعض وملفات في المكان المناسب للجزء الأول من ملف XML ؛ ومع ذلك ، بعد أن يفعل ذلك بشكل صحيح ، يستمر عبوره بشكل غير صحيح. لست متأكدًا تمامًا لماذا ....
ها هو رمزتي:
def dirToXML(self,directory):
curdir = os.getcwd()
os.chdir(directory)
xmlOutput=""
tree = os.walk(directory)
for root, dirs, files in tree:
pathName = string.split(directory, os.sep)
xmlOutput+="<dir><name><![CDATA["+pathName.pop()+"]]></name>"
if len(files)>0:
xmlOutput+=self.fileToXML(files)
for subdir in dirs:
xmlOutput+=self.dirToXML(os.path.join(root,subdir))
xmlOutput+="</dir>"
os.chdir(curdir)
return xmlOutput
FileToxml ، ببساطة يخرج القائمة ، لذلك لا داعي للقلق بشأن ذلك.
هيكل الدليل هو ببساطة:
images/
images/testing.xml
images/structure.xml
images/Hellos
images/Goodbyes
images/Goodbyes/foo
images/Goodbyes/bar
images/Goodbyes/square
وأصبح ملف XML الناتج:
<structure>
<dir>
<name>images</name>
<files>
<file>
<name>structure.xml</name>
</file>
<file>
<name>testing.xml</name>
</file>
</files>
<dir>
<name>Hellos</name>
</dir>
<dir>
<name>Goodbyes</name>
<dir>
<name>foo</name>
</dir>
<dir>
<name>bar</name>
</dir>
<dir>
<name>square</name>
</dir>
</dir>
<dir>
<name>foo</name>
</dir>
<dir>
<name>bar</name>
</dir>
<dir>
<name>square</name>
</dir>
</dir>
<dir>
<name>Hellos</name>
</dir>
<dir>
<name>Goodbyes</name>
<dir>
<name>foo</name>
</dir>
<dir>
<name>bar</name>
</dir>
<dir>
<name>square</name>
</dir>
</dir>
<dir>
<name>foo</name>
</dir>
<dir>
<name>bar</name>
</dir>
<dir>
<name>square</name>
</dir>
</structure>
أي مساعدة سيكون محل تقدير كبير!
المحلول
أوصي بعدم الاستخدام os.walk()
, ، بما أنك يجب أن تفعل الكثير لتدليك ناتجها. بدلاً من ذلك ، ما عليك سوى استخدام وظيفة عودية تستخدم os.listdir()
, os.path.join()
, os.path.isdir()
, ، إلخ.
import os
from xml.sax.saxutils import escape as xml_escape
def DirAsXML(path):
result = '<dir>\n<name>%s</name>\n' % xml_escape(os.path.basename(path))
dirs = []
files = []
for item in os.listdir(path):
itempath = os.path.join(path, item)
if os.path.isdir(itempath):
dirs.append(item)
elif os.path.isfile(itempath):
files.append(item)
if files:
result += ' <files>\n' \
+ '\n'.join(' <file>\n <name>%s</name>\n </file>'
% xml_escape(f) for f in files) + '\n </files>\n'
if dirs:
for d in dirs:
x = DirAsXML(os.path.join(path, d))
result += '\n'.join(' ' + line for line in x.split('\n'))
result += '</dir>'
return result
if __name__ == '__main__':
print '<structure>\n' + DirAsXML(os.getcwd()) + '\n</structure>'
أنا شخصياً أوصي بمخطط XML أقل بكثير ، ووضع أسماء في سمات والتخلص من <files>
مجموعة:
import os
from xml.sax.saxutils import quoteattr as xml_quoteattr
def DirAsLessXML(path):
result = '<dir name=%s>\n' % xml_quoteattr(os.path.basename(path))
for item in os.listdir(path):
itempath = os.path.join(path, item)
if os.path.isdir(itempath):
result += '\n'.join(' ' + line for line in
DirAsLessXML(os.path.join(path, item)).split('\n'))
elif os.path.isfile(itempath):
result += ' <file name=%s />\n' % xml_quoteattr(item)
result += '</dir>'
return result
if __name__ == '__main__':
print '<structure>\n' + DirAsLessXML(os.getcwd()) + '\n</structure>'
هذا يعطي ناتج مثل:
<structure>
<dir name="local">
<dir name=".hg">
<file name="00changelog.i" />
<file name="branch" />
<file name="branch.cache" />
<file name="dirstate" />
<file name="hgrc" />
<file name="requires" />
<dir name="store">
<file name="00changelog.i" />
إلخ.
لو os.walk()
عملت أكثر مثل expat
عمليات الاسترجاعات ، سيكون لديك وقت أسهل منه.
نصائح أخرى
قم بإزالة الخطين:
for subdir in dirs:
xmlOutput+=self.dirToXML(os.path.join(root,subdir))
أنت تتكرر في الدلائل الفرعية. لكن هذا زائد ، لأن OS.Walk يتكرر نفسه.
كنت أحاول استخدام OS.Walk ، لكنني رأيت أنه لم ينجح مع بنية الشجرة العودية التي أردت إنشاءها في XML. لقد قمت بتعديل الكود الخاص بي على النحو التالي وينتج النتيجة التي أحتاجها:
def dirToXML(self,directory):
curdir = os.getcwd()
os.chdir(directory)
xmlOutput=""
pathName = string.split(directory, os.sep)
xmlOutput+="<dir><name><![CDATA["+pathName.pop()+"]]></name>"
for item in os.listdir(directory):
if os.path.isfile(os.path.join(directory, item)):
xmlOutput+="<file><name><![CDATA["+item+"]]></name></file>"
else :
xmlOutput+=self.dirToXML(os.path.join(directory,item))
xmlOutput+="</dir>"
os.chdir(curdir)
return xmlOutput