2014-09-12 5 views
0

У меня есть шейп-файл, который я преобразовываю в файл .xml для использования в MATSim. Структура файла выглядит следующим образом:Вывести график как `.xml`

<?xml version="1.0" encoding="UTF-8"?> 
<!DOCTYPE network SYSTEM "http://www.matsim.org/files/dtd/network_v1.dtd"> 
<network name="VISUM export national network 2007-11-28"> 

<!-- ====================================================================== --> 
    <nodes> 
     <node id="1000" x="730065.3125" y="220415.9531" type="2" origid="1000" /> 
     <node id="1001" x="731010.5" y="220146.2969" type="2" origid="1001" /> 
     ..... 
    </nodes> 
<!-- ====================================================================== --> 
    <links capperiod="01:00:00" effectivecellsize="7.5" effectivelanewidth="3.75"> 
     <link id="100365" from="226" to="227" length="921.0" freespeed="33.3333333333333" capacity="5600.0" permlanes="2.0" oneway="1" modes="car" origid="183" type="10" /> 
    ... 
    </links> 
<!-- ====================================================================== --> 
</network> 

Я делаю это с библиотекой NetworkX Python, который может читать шейп в виде графа, и экспортировать график как GEXF объекта. Этот код (по существу) выводит что-то близко, но не достаточно близко, к спецификации сети.

import networkx as nx 

G = nx.read_shp("expcuts1.shp") 
start = 0 
G = nx.convert_node_labels_to_integers(G, first_label=start, 
     label_attribute = "coord") 

# Build a new object with the elements that you need 
H = nx.DiGraph(name = "Python NetworkX export from FAF 3.4") 
H.add_edges_from(G.edges()) 

# store coordinates in node attributes 
for i in range(len(H)): 
    H.node[i]['x'] = G.node[i]['coord'][0] 
    H.node[i]['y'] = G.node[i]['coord'][1] 

# export as xml (really, gexl, but that's pretty close) 
nx.write_gexf(H, 'test.xml') 
<gexf version="1.1" xmlns="http://www.gexf.net/1.1draft" xmlns:viz="http://www.gexf.net/1.1draft/viz" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.w3.org/2001/XMLSchema-instance"> 
    <graph defaultedgetype="undirected" mode="static"> 
    <attributes class="node" mode="static"> 
     <attribute id="0" title="y" type="double" /> 
     <attribute id="1" title="x" type="double" /> 
    </attributes> 
    <nodes> 
     <node id="0" label="0"> 
     <attvalues> 
      <attvalue for="0" value="1389860.27495" /> 
      <attvalue for="1" value="2237913.99085" /> 
     </attvalues> 
     </node> 

В дополнение к этому, GEXL использует узлы и края, но словарный запас MATSim запрашивает узлов и ссылок. Я пытаюсь решить, будет ли проще настраивать функцию write_gexf из NetworkX или записывать в XML вручную, например, с помощью ElementTree API. Какие-нибудь советы?

+0

Можете ли вы с уверенностью сказать, что график ацикличен? Если нет, что делать с циклами? – Phonon

+0

График, безусловно, цикличен; он представляет собой сеть автомагистралей. Однако график не обязательно должен быть направлен. Я могу создать 'H' как либо' Граф', либо 'DiGraph', и результат тот же. – gregmacfarlane

ответ

0

Короткие: Подстройте функцию write_gexf от NetworkX, если это разовый проект.

Long:

Для MATSim вам нужен ориентированный граф. Gexf позволяет это defaultedgetype="directed". Вы можете добавить дополнительные атрибуты к краям, например. мощность, полосы ...

<edge weight="1.0" target="109001663" source="109001672" label="network link" id="99999"> 
<attvalues> 
    <attvalue start="0.0" value="0" for="capacity"/> 
    <attvalue start="0.0" value="0" for="length"/> 
</attvalues> 
</edge> 

Поскольку у вас уже есть gexf последний шаг преобразования один к одному. Узлы Gexf напрямую переходят на узлы MATSim, а ребра - это ссылки в терминологии MATSim. Однако вам необходимо предоставить MATSim атрибуты сети.

Узлы просто нужно х, у-координаты

Для ссылок вы можете добавить фактическую длину линии (не евклидово расстояние). Кроме того, вам потребуется максимально допустимая скорость (freespeed), емкость (обычно заданная в PCU в час) и количество полос движения.

Обратите внимание, что мощность зависит от капериода, то есть capperiod="01:00:00" означает действительный в течение одного часа.

P.S. Вы также можете посмотреть the gexf package, где вы найдете некоторые вспомогательные классы gexf, в основном для преобразования сетей MATSim в gexf, например. для анализа их в Gephi.