Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/357.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用卷积窗口(python)隔离海岸网格_Python_Numpy_Image Processing_Scipy - Fatal编程技术网

使用卷积窗口(python)隔离海岸网格

使用卷积窗口(python)隔离海岸网格,python,numpy,image-processing,scipy,Python,Numpy,Image Processing,Scipy,我正在尝试从数据集中隔离海岸网格。我可以通过单独检查陆地网格的每个邻居来完成,如果8个邻居中有一个是海洋网格,那么我正在保存网格。以下是我编写的函数: def coastalGrids(ds): grid=~out[0,:,:].mask #out is a 3D masked array (time,lat,lon) #At each grid where there is land, check all its 8 neighbors, #and if any of them are o

我正在尝试从数据集中隔离海岸网格。我可以通过单独检查陆地网格的每个邻居来完成,如果8个邻居中有一个是海洋网格,那么我正在保存网格。以下是我编写的函数:

def coastalGrids(ds):
grid=~out[0,:,:].mask #out is a 3D masked array (time,lat,lon)

#At each grid where there is land, check all its 8 neighbors, 
#and if any of them are ocean, save the grid to the dataset
coastline=np.zeros(grid.shape, dtype=bool)
for i in range(1,len(lat)-1):
    for j in range(1,len(lon)-1):
        if grid[i,j]==True:
            if (grid[i+1,j+1]!=True):
                coastline[i,j]= grid[i,j]
            elif (grid[i+1,j]!=True):
                coastline[i,j]= grid[i,j]
            elif (grid[i+1,j-1]!=True):
                coastline[i,j]= grid[i,j]
            elif (grid[i,j+1]!=True):
                coastline[i,j]= grid[i,j]
            elif (grid[i,j-1]!=True):
                coastline[i,j]= grid[i,j]
            elif (grid[i-1,j+1]!=True):
                coastline[i,j]= grid[i,j]
            elif (grid[i-1,j]!=True):
                coastline[i,j]= grid[i,j]
            elif (grid[i-1,j-1]!=True):
                coastline[i,j]= grid[i,j]
return coastline
我想知道:

  • 有一种不那么丑陋的方法可以做到这一点,比如说使用scipy的卷积windows函数
  • 扩展这种功能,有没有办法将陆地网格与海岸线隔离10个网格

  • 谢谢

    我不确定scipy的卷积功能,但上面的一个版本更简洁,它可以循环置换索引:

    neighbours = [(1,1), (1,0), (1,-1), (0,1),
                  (0,1), (-1,1), (-1, 0), (-1,-1)]
    for i in range(1,len(lat)-1):
        for j in range(1,len(lon)-1):
            if grid[i,j]==True:
                for (di, dj) in neighbours:
                    if (grid[i+di,j+dj] != True:
                        coastline[i,j]= grid[i,j]
                        break
    

    我不确定scipy的卷积功能,但上面的一个版本更简洁一些,就是循环置换索引:

    neighbours = [(1,1), (1,0), (1,-1), (0,1),
                  (0,1), (-1,1), (-1, 0), (-1,-1)]
    for i in range(1,len(lat)-1):
        for j in range(1,len(lon)-1):
            if grid[i,j]==True:
                for (di, dj) in neighbours:
                    if (grid[i+di,j+dj] != True:
                        coastline[i,j]= grid[i,j]
                        break
    
    使用图像形态学算子 您当前所做的操作相当于原始布尔数组与其属性之间的差异

    这与定义密切相关,但定义略有不同

    无论如何,假设我们有一个非常简单的岛:

    import numpy as np
    import matplotlib.pyplot as plt
    
    y, x = np.mgrid[-10:10:20j, -10:10:20j]
    land = np.hypot(x, y) < 7
    
    fig, ax = plt.subplots()
    ax.pcolormesh(land, cmap='gray', edgecolor='gray', antialiased=True)
    plt.show()
    

    然后看看有什么不同:

    coast = land != erosion
    


    正方形与对角连通性 默认情况下,这使用“方形”连接。换句话说,对角线不算是接触。默认结构(也称为“footprint”)如下所示:

    [[0, 1, 0],
     [1, 1, 1],
     [0, 1, 0]]
    
    [[1, 1, 1],
     [1, 1, 1],
     [1, 1, 1]]
    
    在您的代码中,假设对角线相接触。在这种情况下,您需要“完全”连接,并且结构如下所示:

    [[0, 1, 0],
     [1, 1, 1],
     [0, 1, 0]]
    
    [[1, 1, 1],
     [1, 1, 1],
     [1, 1, 1]]
    
    为此,我们将指定类似的内容:

    erosion = scipy.ndimage.binary_erosion(land, structure=np.ones((3,3)))
    
    作为一个完整的例子:

    import numpy as np
    import matplotlib.pyplot as plt
    import scipy.ndimage
    
    y, x = np.mgrid[-10:10:20j, -10:10:20j]
    land = np.hypot(x, y) < 7
    
    erosion = scipy.ndimage.binary_erosion(land, structure=np.ones((3,3)))
    coast = land != erosion
    
    fig, ax = plt.subplots()
    ax.pcolormesh(coast, cmap='gray', edgecolor='gray', antialiased=True)
    plt.show()
    
    将numpy导入为np
    将matplotlib.pyplot作为plt导入
    导入scipy.ndimage
    y、 x=np.mgrid[-10:10:20j,-10:10:20j]
    陆面=np.hypot(x,y)<7
    侵蚀=scipy.ndimage.binary_侵蚀(土地,结构=np.one((3,3)))
    海岸=陆地!=腐蚀
    图,ax=plt.子批次()
    ax.pcolormesh(coast,cmap='gray',edgecolor='gray',抗锯齿=True)
    plt.show()
    

    使用形态学梯度

    你也可以考虑使用形态梯度算子。这是给定输入和连接足迹的二进制膨胀和二进制侵蚀之间的差异

    在您的例子中,它还将包括与陆地相邻的海洋像素,以及与海洋相邻的陆地像素。实际上,它会给你更厚的边界

    例如:

    import numpy as np
    import matplotlib.pyplot as plt
    import scipy.ndimage
    
    y, x = np.mgrid[-10:10:20j, -10:10:20j]
    land = np.hypot(x, y) < 7
    
    coast = scipy.ndimage.morphological_gradient(land,
                                                footprint=[[0, 1, 0],
                                                           [1, 1, 1],
                                                           [0, 1, 0]])
    
    fig, ax = plt.subplots()
    ax.pcolormesh(coast, cmap='gray', edgecolor='gray', antialiased=True)
    plt.show()
    
    将numpy导入为np
    将matplotlib.pyplot作为plt导入
    导入scipy.ndimage
    y、 x=np.mgrid[-10:10:20j,-10:10:20j]
    陆面=np.hypot(x,y)<7
    海岸=scipy.ndimage.形态梯度(陆地,
    footprint=[[0,1,0],
    [1, 1, 1],
    [0, 1, 0]])
    图,ax=plt.子批次()
    ax.pcolormesh(coast,cmap='gray',edgecolor='gray',抗锯齿=True)
    plt.show()
    

    使用图像形态学操作符 您当前所做的操作相当于原始布尔数组与其属性之间的差异

    这与定义密切相关,但定义略有不同

    无论如何,假设我们有一个非常简单的岛:

    import numpy as np
    import matplotlib.pyplot as plt
    
    y, x = np.mgrid[-10:10:20j, -10:10:20j]
    land = np.hypot(x, y) < 7
    
    fig, ax = plt.subplots()
    ax.pcolormesh(land, cmap='gray', edgecolor='gray', antialiased=True)
    plt.show()
    

    然后看看有什么不同:

    coast = land != erosion
    


    正方形与对角连通性 默认情况下,这使用“方形”连接。换句话说,对角线不算是接触。默认结构(也称为“footprint”)如下所示:

    [[0, 1, 0],
     [1, 1, 1],
     [0, 1, 0]]
    
    [[1, 1, 1],
     [1, 1, 1],
     [1, 1, 1]]
    
    在您的代码中,假设对角线相接触。在这种情况下,您需要“完全”连接,并且结构如下所示:

    [[0, 1, 0],
     [1, 1, 1],
     [0, 1, 0]]
    
    [[1, 1, 1],
     [1, 1, 1],
     [1, 1, 1]]
    
    为此,我们将指定类似的内容:

    erosion = scipy.ndimage.binary_erosion(land, structure=np.ones((3,3)))
    
    作为一个完整的例子:

    import numpy as np
    import matplotlib.pyplot as plt
    import scipy.ndimage
    
    y, x = np.mgrid[-10:10:20j, -10:10:20j]
    land = np.hypot(x, y) < 7
    
    erosion = scipy.ndimage.binary_erosion(land, structure=np.ones((3,3)))
    coast = land != erosion
    
    fig, ax = plt.subplots()
    ax.pcolormesh(coast, cmap='gray', edgecolor='gray', antialiased=True)
    plt.show()
    
    将numpy导入为np
    将matplotlib.pyplot作为plt导入
    导入scipy.ndimage
    y、 x=np.mgrid[-10:10:20j,-10:10:20j]
    陆面=np.hypot(x,y)<7
    侵蚀=scipy.ndimage.binary_侵蚀(土地,结构=np.one((3,3)))
    海岸=陆地!=腐蚀
    图,ax=plt.子批次()
    ax.pcolormesh(coast,cmap='gray',edgecolor='gray',抗锯齿=True)
    plt.show()
    

    使用形态学梯度

    你也可以考虑使用形态梯度算子。这是给定输入和连接足迹的二进制膨胀和二进制侵蚀之间的差异

    在您的例子中,它还将包括与陆地相邻的海洋像素,以及与海洋相邻的陆地像素。实际上,它会给你更厚的边界

    例如:

    import numpy as np
    import matplotlib.pyplot as plt
    import scipy.ndimage
    
    y, x = np.mgrid[-10:10:20j, -10:10:20j]
    land = np.hypot(x, y) < 7
    
    coast = scipy.ndimage.morphological_gradient(land,
                                                footprint=[[0, 1, 0],
                                                           [1, 1, 1],
                                                           [0, 1, 0]])
    
    fig, ax = plt.subplots()
    ax.pcolormesh(coast, cmap='gray', edgecolor='gray', antialiased=True)
    plt.show()
    
    将numpy导入为np
    将matplotlib.pyplot作为plt导入
    导入scipy.ndimage
    y、 x=np.mgrid[-10:10:20j,-10:10:20j]
    陆面=np.hypot(x,y)<7
    海岸=scipy.ndimage.形态梯度(陆地,
    footprint=[[0,1,0],
    [1, 1, 1],
    [0, 1, 0]])
    图,ax=plt.子批次()
    ax.pcolormesh(coast,cmap='gray',edgecolor='gray',抗锯齿=True)
    plt.show()
    

    谢谢你,乔,不仅为我的问题提供了完美的解决方案,而且还为我介绍了数学形态学这一领域。增加scipy.ndimage.binary_corporation()函数中的“structure”窗口,也解决了我的第二个问题(将内陆网格与海岸线隔离到一定半径)!谢谢你,乔,不仅为我的问题提供了一个完美的解决方案,而且还为我介绍了数学形态学这个领域。增加scipy.ndimage.binary_corporation()函数中的“structure”窗口,也解决了我的第二个问题(将内陆网格与海岸线隔离到一定半径)!