如何在python中将skimage骨架信息提取到NetworkX节点和边缘以进行进一步的高级分析 [英] How to extract skimage skeleton information to NetworkX nodes and edges in python for further advanced analysis

查看:83
本文介绍了如何在python中将skimage骨架信息提取到NetworkX节点和边缘以进行进一步的高级分析的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

目前,我在python中使用skimage来从一些二值化地图中提取开放空间的骨架,如下图所示,

Currently, I use skimage in python to extract the skeleton of open space from some a binarized map as following pictures,

使用以下python代码:

With following python codes:

from skimage.morphology import skeletonize
from skimage import draw
from skimage.io import imread, imshow
from skimage.color import rgb2gray

# load image from file
img_fname=os.path.join('images','mall1_2F_schema.png') 
image=imread(img_fname)

# Change RGB color to gray 
image=rgb2gray(image)

# Change gray image to binary
image=np.where(image>np.mean(image),1.0,0.0)

# perform skeletonization
skeleton = skeletonize(image)

现在,我想从骨骼中提取端点和交叉点作为Networkx图对象的节点,同时计算相邻节点之间的距离作为Networkx Graph对象的边缘.当前,我必须手动获取点坐标并将其输入到NetworkX对象初始化过程中,我们是否有更聪明的方法来自动完成所有操作?

Now I would like to extract the end points and cross points from the skeleton as nodes for Networkx graph object while calculating the distance between the neighboring nodes as edges for Networkx Graph object. Currently, I have to manually get the point coordinates and input to NetworkX object initialization process, do we have any smarter way to do everything automatically?

顺便说一句,我发现 yaron kahanovitch

By the way, I found yaron kahanovitch's answer to the question on stackoverflow proposes similar approaches. However, no more realization suggestions was given, and I think NetworkX could be one approach.

非常感谢您的任何建议.

Any suggestions from you are greatly appreciated.

推荐答案

在这里.

这段代码用于2D骨架图像,您可以轻松地将其扩展到3D.

This piece of code is for 2D skeleton image and you can easily extend it to 3D.

import networkx as nx
import numpy as np

def skeleton_image_to_graph(skeIm, connectivity=2):
    assert(len(skeIm.shape) == 2)
    skeImPos = np.stack(np.where(skeIm))
    skeImPosIm = np.zeros_like(skeIm, dtype=np.int)
    skeImPosIm[skeImPos[0], skeImPos[1]] = np.arange(0, skeImPos.shape[1])
    g = nx.Graph()
    if connectivity == 1:
        neigh = np.array([[0, 1], [0, -1], [1, 0], [-1, 0]])
    elif connectivity == 2:
        neigh = np.array([[0, 1], [0, -1], [1, 0], [-1, 0], [1, 1], [1, -1], [-1, 1], [-1, -1]])
    else:
        raise ValueError(f'unsupported connectivity {connectivity}')
    for idx in range(skeImPos[0].shape[0]):
        for neighIdx in range(neigh.shape[0]):
            curNeighPos = skeImPos[:, idx] + neigh[neighIdx]
            if np.any(curNeighPos<0) or np.any(curNeighPos>=skeIm.shape):
                continue
            if skeIm[curNeighPos[0], curNeighPos[1]] > 0:
                g.add_edge(skeImPosIm[skeImPos[0, idx], skeImPos[1, idx]], skeImPosIm[curNeighPos[0], curNeighPos[1]], weight=np.linalg.norm(neigh[neighIdx]))
    g.graph['physicalPos'] = skeImPos.T
    return g

这篇关于如何在python中将skimage骨架信息提取到NetworkX节点和边缘以进行进一步的高级分析的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆