數據分析學習筆記(三)-NetworkX的使用


轉:http://baiyejianxin.iteye.com/blog/1764048
創建簡單的空圖形(沒有邊和點)
    
    import networkx as nx
    g = nx.Graph();
    
    h = nx.Graph( g);    #可以在構建Graph對象時指定值來構造一個新的Graph對象
 
    f = nx.Graph( [ (1,2),(2,3),(1,3)]);  #可以在構建Graph對象時指定node關系的數組來構建Graph對象
 
    根據定義,一個Graph就是一個所有nodes的集合。在NetworkX中,nodes能夠代表任何對象,例如一個文本,一個圖片,一個xml對象或者另外一個Graph,一個自定義的對象等等。
    由於NetworkX提供了多種Graph對象生成方法,並且體痛了讀寫方法來讀寫多種格式,所以Graph對象能夠使用多種方式創建。
 
----------------------
Nodes
    
    graph對象能夠添加node(節點)
 
    g.add_node(1);   #添加一個節點    
    g.add_nodes_from( [2,3])   #添加一個節點列表
    
    h = nx.path_graph(10)
    g.add_nodes_from( h)  #添加一個能夠迭代的集合(例如:list, set, graph, file等等),這樣g中包含了h中的元素
    g.add_node( h)    #這是將h作為一個node添加到g中
    g.add_nodes_from( 'span');   #將span拆分為一個字符數組,然后添加node
 
    Note: 最后,h是一個graph對象,將h最為g的node,是一個很靈活的特性。這樣節點可以是graph中的graph,files中的graphs,method中的graph等等。值得思考的是,如果結構化你的應用使得那些node都是有用的實體。如果你願意,你還可以是g對應一個唯一的表示,每個node對應一個被表示的key。如果node對應的是對象中的內容,那么當內容變化是,不應該修改對象,應該修改node對應的內容(有點繞)。
 
-----------------------
Edges
 
    graph對象中還能夠添加edges(邊);
    
    g.add_edge(1,2)    # 添加一個1和2之間的edge
    e=(2,3)                   #定義個關系
    g.add_edge( *e)    #添加關系對象
 
    g.add_edges_from([(1,2),(2,3)])  #添加一個edge數組
    g.add_edges_from( h.edges());   #h.edges()返回的h的包含所有edge的數組
 
    #拆除graph對象中的node和edge可以使用如下方法
    g.remove_node()
    g.remove_nodes_from()
    g.remove_edge()
    g.remove_edges_from()
 
    #刪除所有的node和edge
    g.clear();
 
    #如果重復添加相同的node和edge,NetworkX將會將會忽略那些重復的內容。
    g.add_nodes_from("span");
    g.add_node( "s");
    
    #獲取一個Graph對象中node和edge的數量
    g.number_of_nodes();
    g.number_of_edges();
 
    #獲取一個Graph對象中的node數組或者edge數組
    g.nodes();
    g.edges();
 
    g.neighbors(1);   #獲取與node為1相鄰的node是節點
    g.remove_edge( 1,2);   #刪除node1和node2之間的edge,自此node1和node2不再為相鄰的node
 
 
------------------------------
如何使用nodes和edges?
    
    獲取你已經注意到了node和edge並不是Graph的對象。這就能夠使你更加靈活的使用node和edge,如果在python中使用string和number。node可以為任何hashable對象(除了Node),edge還可以和其他Graph對象中的node建立關聯。例如:
 
        g.add_node( n1, n2, Graph=x);
 
        例如,n1,n2可以代表生物蛋白質資料庫中兩種蛋白質對象,x可以是代表一個觀察實驗出版物中的xml片段記錄。
        
        如果熟悉他們,那么他們會非常有用。如果濫用也會帶來意想不到的結果。如有疑問可以通過convert_node_labels_to_integers()方法來獲得更多的有整數組成的傳統圖形。
 
-------------------------
除了使用上面提到的方法外,可以使用索引下標來訪問edge
    
    >>>g[1]
    {2,{}}
    >>>g[1][1]
    {}
    
    Note:不要修改返回到額字典結構,它是graph固有的一部分,直接修改會導致不一致的狀態
 
    同樣通過下標可以設置edge的屬性
    
    g.add_edge( 1, 3)
    g[1][1][ "color"] = "blue"
 
    通過迭代快速查找所有的edge
>>> FG=nx.Graph() >>> FG.add_weighted_edges_from([(1,2,0.125),(1,3,0.75),(2,4,1.2),(3,4,0.375)]) >>> for n,nbrs in FG.adjacency_iter(): ... for nbr,eattr in nbrs.items(): ... data=eattr['weight'] ... if data<0.5: print('(%d, %d, %.3f)' % (n,nbr,data)) (1, 2, 0.125) (2, 1, 0.125) (3, 4, 0.375) (4, 3, 0.375)
 
 
--------------------
添加graph,node,edge的屬性
 
        像color,label,weight或者其他Python對象的屬性都可以被設置為graph,node,edge的屬性。
 
        每個graph,node,edge都能夠包含key/value這樣的字典數據。默認情況下是沒有這些屬性的。可以通過add_node(),add_edge(),或者直接修改來添加和修改屬性。
 
         Graph 屬性
            
            g = nx.Graph( day="friday");
            g.graph
            打印:{“day”:“friday”}
    
            g.graph["day"]="Monday";
            g.graph
            打印:{"day":"Monday"}
 
         Node屬性
 
            通過add_node(),add_nodes_from或者g.node來添加屬性
 
            g.add_node( 1, time="5pm");
            g.add_nodes_from([3], time="2pm");
            g.node[ 1]
            打印:{"time":"5pm"}
            g.node[1]["room"]=714;
            g.nodes(data=True);
            打印:[(1,{"room":714, "time":"5pm"}),(3,{"time":"2pm"})]
 
            Note:向node添加屬性並不會想graph添加屬性,
 
         Edge屬性
 
            通過add_edge(), add_edges_from()或者g.edge來添加屬性
 
            g.add_edge(1,2,wegiht=4.7)
            g.add_edges_from( [ (2,3),(3,4) ], color="red")
            g.add_edges_from( [(1,2,{"color":"blue"}),(4,5,{"weight":8})])
            g[1][2]["width"]=4.7
            g.edge[1][2]["weight"]=4
 
 
-----------------------------
Directed graphs(有向圖)
        
            DiGraph類針對有向edge提供了另外的方法,例如:out_edges(), in_degree(),predecessors(),successors()等。為了是算法能夠正常運行,有向版本的neighbors()和degree()對於seccessor()方法是相同的。in_degree()和out_degree()都是獨自的。
            
            ig = nx.DiGraph()
            ig.add_wieghted_edges_from( [(1,2,0.5),(2,3,0.7)])
            ig.out_degree( 1,weight="weight");
            打印:0.5
            ig.degree( 1, weight="weight");
            打印:1.25
            ig.seccessors(1)
            打印:[2]
            ig.neighbors(1)
            打印:[2]
 
        一些算法只對有向grapsh起作用,其他算法沒有明確定義。同時使用有向graph和無向graph是非常危險的事情。如果想將有向graph轉換為無向graph可以使用
        
            Graph.to_undirected()
 
            或者
            
            h = nx.Graph( g)
 
-------------------
Multigraphs
    
            NetworkX提供了類來實現一對node之間存在多個edge的實現類:MultiGraph和MultiDiGraph,他們都允許使用的edge數據添加多個的edge。對於某些應這個特性非常有用,但是很多算法在這種graph中並沒有明確定義。
 
>>> MG=nx.MultiGraph() >>> MG.add_weighted_edges_from([(1,2,.5), (1,2,.75), (2,3,.5)]) >>> MG.degree(weight='weight') {1: 1.25, 2: 1.75, 3: 0.5} >>> GG=nx.Graph() >>> for n,nbrs in MG.adjacency_iter(): ... for nbr,edict in nbrs.items(): ... minvalue=min([d['weight'] for d in edict.values()]) ... GG.add_edge(n,nbr, weight = minvalue) ... >>> nx.shortest_path(GG,1,3) [1, 2, 3]
 
---------------------
Graph generators and graph operations(圖形生成和操作)
 
        為了構建node-by-node或者edge-by-edge的graph,還可以使用以下方式。
 
        subgraph( G, nbunch)
        union( g1,g2)                 #合並praph
        disjoint_union( g1, g2) #假設所有node都不相同合並praph
        cartesian_product( g1, g2)  #返回笛卡爾產品praph
        compose( g1, g2)                 #合並公共的node
        complement( g1)                 #praph的補集
        create_empty_copy( g)        #返回某個praph對象的空的拷貝對象
        convert_to_undirected( g)   #返回一個無向praph
        convert_to_directed( g)       #返回一個有向的praph
 
        使用小圖的調用
 
        petersen = nx.petersen_parph();
        tutte = nx.tutte_praph()
        maze = nx.sedgewick_maze_praph()
        tet = nx.tetrahedral_praph()
 
        使用典型praph的構造生成器
        
        k_4 = nx.complete_graph(4);
        k_3_5 = nx.complete_bipartite_graph(3,5)
        barbell = nx.barbell_graph( 10, 10)
        lollipop = nx.lollipop_graph( 10,20);
 
        使用隨機graph生成器
 
>>> er=nx.erdos_renyi_graph(100,0.15) >>> ws=nx.watts_strogatz_graph(30,3,0.1) >>> ba=nx.barabasi_albert_graph(100,5) >>> red=nx.random_lobster(100,0.9,0.9)
        從存儲praph的文件中讀取格式數據然后生成praph。
>>> nx.write_gml(red,"path.to.file") >>> mygraph=nx.read_gml("path.to.file")
--------------
Analyzing graphs(分析圖)
 
    結構話的praph能夠使用提供的方法來進行分析:
 
        g = nx.Graph()
        g.add_edges_from( [(1,2),(1,3)])
        g.add_node( "spam")
 
        nx.connected_components( g)   #將node有關聯的顯示一個數組中。返回的為一個數組
        打印: [ [1,2,3], [ "spam"]]
 
        sorted( nx.degree( g).values())
        打印: [ 0, 1, 1, 2]
 
        nx.clustering( g)   #聚合
        打印: { 1 : 0.0, 2:0.0 , 3: 0.0 . "spam":0.0}
 
        nx.degree( g)        #顯示等級
        打印:{1:2, 2:1,3:1,"spam":0}
 
        
        對於特殊的node,可以將一個單獨的node或者node集合作為參數。如果傳入一個獨立的node,那么返回一個獨立的值,如果傳入一個node集合,這個方法將返回一個字典類型的數據    
        
        nx.degree(g,1)        #返回第一個node的值
        2
        
        g.degree( 1)           #返回第一個node的值
        2
 
        g.degree( 1, 2)       #返回從第一個node開始,前兩個node的值
        {1:2, 2:1}
 
        sorted( g.degree( [ 1, 2]).values())  #返回1和2並排序輸出結果
        [1,2]
 
        sorted( g.degree().values())            #返回g中node的權重,並排序輸出結果
 
        想要了解更加詳細的算法只是,參考: 算法
 
---------------------
Drawing Praphs(繪制圖形)
    
        NetworkX並不是首選的圖形繪制包,但是它包含了基本的圖形繪制工具開源包Matplotlib。如果需要的話可以引入network.drawing包。(更詳細的文檔參考: Drawing
 
        注意: NetworkX中的繪圖包不和Python3兼容
        
        首先引入 Matplotlib的plot接口
 
        import matplotlib.pyplot as plt
 
        如果成功引入 networkx.drawing那么可以使用下面的方法繪制graph對象
 
        nx.draw( g)
        nx.draw_random( g)
        nx.draw_circular( g)
        nx.draw_spectral( g)
 
        將繪制的內容保存的一個文件中使用下面的方法
        nx.draw( g)
        plt.savefig( "path.png")
 
數據分析學習筆記(四)-使用NetworkX進行數據分析的實例


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM