2017-05-17 30 views
-1

這是我想使用的xml文件 我試圖創建一個名爲'dict1'的字典 它應該包含鍵「P​​ocket_substation」和「sub_substation」 ,第一個鍵Pocket_substation應該包含所有的input_names,而sub_substation鍵應該包含所有的output_names。」我想在一個類中支持以下功能的結果:...「

<input_layer name = "Pocket_Substation"/> 

<output_layer name = "sub_substation"/> 

<field_mapping> 

    <field input_name = "dat" output_name="date" /> 

    <field input_name = "Type" output_name="type"/> 

    <field input_name = "Class" output_name="class"/> 

    <field input_name = "Land" output_name="land"/> 

    <field input_name = "status" output_name="status"/> 

    <field input_name = "descrp" output_name="description"/> 

    <field input_name = "Loc" output_name="location"/> 

    <field input_name = "voltage" output_name="voltage"/> 

    <field input_name = "name" output_name="owner_name"/> 


    <field input_name = "Remarks" output_name="remarks"/> 

</field_mapping> 

,並選擇所有input_names我寫

for elem in tree.iter(tag='field'): 

print elem.attrib 

for ele in elem.attrib(tag='input_name'): 

    print ele.attrib 

,但只打印第一個值。有人幫我在代碼中解決這個 功能:

def read_field(xml_node, name): 

return [child.get(name) for child in xml_node.iter('field')] 

def read_map(xml_node): 

f = root.attrib 

dict1 = {f['name']:['input_layer','output_layer','fields']} 

dict1[f['name']][0] = {'input_layer':root.find('input_layer').get('name')} 

dict1[f['name']][1] = {'output_layer':root.find('output_layer').get('name')} 

for child in xml_node: 

    if child.tag == 'field_mapping': 

     fields = {field_name : read_field(child, field_name) for field_name 

       in ['input_name','output_name']} 

     dict1[f['name']][2] = 

     {'fields':dict(zip(fields['output_name'],fields['input_name']))} 

return dict1 
+0

你在使用ElementTree嗎?您還可以添加更多的代碼,以便我們看到您如何訪問這些元素? –

+0

進口xml.etree.ElementTree如ET 樹= ET.parse( 'substation.xml') 根= tree.getroot() 用於child_of_root在根: \t打印child_of_root.tag 它給所有的孩子的根。 在tree.iter()ELEM: \t打印elem.tag,elem.attrib 它給所有的屬性 但我不能分開「input_name」和「output_name中」屬性 –

+0

@Elango我已經編輯了答案並展示瞭如何使用ElementTree來完成。請檢查。 –

回答

1

首先,您需要將XML條目包裝成類似...的東西,因爲否則它在語法上不正確。

以外,你可以分析你的映射是這樣的:

import xml.etree.ElementTree as ET 

def read_field_attributes(xml_node, name): 
    return [child.get(name) for child in xml_node.iter('field')] 

def read_mapping(xml_node): 
    # reset the variables 
    input_layer = None 
    output_layer = None 
    fields = dict() 
    # loop over the first level nodes and store the values 
    for child in xml_node: 
     if child.tag == 'field_mapping': 
      # read the input and output fields separate but in order 
      fields = {field_name : read_field_attributes(child, field_name) for field_name in ['input_name', 'output_name']} 
     elif child.tag == 'input_layer': 
      # read the name of the input layer 
      input_layer = child.get('name') 
     elif child.tag == 'output_layer': 
      # read the name of the output layer 
      output_layer = child.get('name') 
    # if all the information is provided, build the mapping 
    if input_layer is not None and output_layer is not None and len(fields) == 2: 
     return { 
      input_layer : fields['input_name'], 
      output_layer : fields['output_name'], 
     } 
    # otherwise, return an empty dictionary 
    return {} 

tree = ET.parse('substation.xml') 
root = tree.getroot() 
print(read_mapping(root)) 

輸出將

{ 
    'Pocket_Substation': 
     ['dat', 'Type', 'Class', 'Land', 'status', 'descrp', 'Loc', 'voltage', 'name', 'Remarks'], 
    'sub_substation': 
     ['date', 'type', 'class', 'land', 'status', 'description', 'location', 'voltage', 'owner_name', 'remarks'] 
} 

然而,分析和存儲輸入和輸出參數是有點危險的,因爲一個的字段可能有輸入,沒有輸出,反之亦然,在解析過程中你不會知道它。相反,我會建議使用字典將輸入映射到輸出,以便每個輸入對應於一個輸出並且只有一個輸出。

+0

謝謝@Pablo Gutierrez Marques。有我想要的輸出。感謝您的即時幫助 –

+0

Hi @Pablo Gutierrez Marques。我需要字典格式的輸出值。 –

+0

''input_layer:fields ['input_name'], output_layer:fields ['output_name'], }'是一個字典。這是否工作,或者你需要一個不同的結構? –

2

可以使用BeautifulSoup解析xml。這很方便。

from bs4 import BeautifulSoup 

soup = BeautifulSoup(your_xml, 'xml') 

print {soup.find('input_layer').get('name'): [item.get('input_name') for item in soup.find_all('field')]} 

它會給你這樣的輸出:如果你想使用xml模塊,爲此,你可以接近這樣

{u'Pocket_Substation': [u'dat', 
    u'Type', 
    u'Class', 
    u'Land', 
    u'status', 
    u'descrp', 
    u'Loc', 
    u'voltage', 
    u'name', 
    u'Remarks']} 

{root.find('input_layer').get('name'): [item.get('input_name') for item in list(root.find('field_mapping'))]} 

這會給你的相同的輸出。

+0

字典應該是什麼樣子? –

+0

謝謝@salman它爲我工作 –

相關問題