Ejemplo n.º 1
0
def run(plotIt=True, n=60):

    M = Mesh.TreeMesh([[(1, 16)], [(1, 16)]], levels=4)

    M = Mesh.TreeMesh([[(1, 16)], [(1, 16)]], levels=4)
    M.insert_cells(np.array([5., 5.]), np.array([3]))
    M.number()

    if plotIt:
        fig, axes = plt.subplots(2, 1, figsize=(10, 10))

        M.plotGrid(cells=True, nodes=False, ax=axes[0])
        axes[0].axis('off')
        axes[0].set_title('Simple QuadTree Mesh')
        axes[0].set_xlim([-1, 17])
        axes[0].set_ylim([-1, 17])

        for ii, loc in zip(range(M.nC), M.gridCC):
            axes[0].text(loc[0] + 0.2, loc[1], '{0:d}'.format(ii), color='r')

        axes[0].plot(M.gridFx[:, 0], M.gridFx[:, 1], 'g>')
        for ii, loc in zip(range(M.nFx), M.gridFx):
            axes[0].text(loc[0] + 0.2, loc[1], '{0:d}'.format(ii), color='g')

        axes[0].plot(M.gridFy[:, 0], M.gridFy[:, 1], 'm^')
        for ii, loc in zip(range(M.nFy), M.gridFy):
            axes[0].text(loc[0] + 0.2,
                         loc[1] + 0.2,
                         '{0:d}'.format((ii + M.nFx)),
                         color='m')

        axes[1].spy(M.faceDiv)
        axes[1].set_title('Face Divergence')
        axes[1].set_ylabel('Cell Number')
        axes[1].set_xlabel('Face Number')
Ejemplo n.º 2
0
    def setUp(self):
        def topo(x):
            return np.sin(x * (2. * np.pi)) * 0.3 + 0.5

        def function(cell):
            r = cell.center - np.array([0.5] * len(cell.center))
            dist1 = np.sqrt(r.dot(r)) - 0.08
            dist2 = np.abs(cell.center[-1] - topo(cell.center[0]))

            dist = min([dist1, dist2])
            # if dist < 0.05:
            #     return 5
            if dist < 0.05:
                return 6
            if dist < 0.2:
                return 5
            if dist < 0.3:
                return 4
            if dist < 1.0:
                return 3
            else:
                return 0

        M = Mesh.TreeMesh([64, 64], levels=6)
        M.refine(function)
        self.M = M
Ejemplo n.º 3
0
def run(plotIt=True):
    """
        Mesh: QuadTree: Hanging Nodes
        =============================

        You can give the refine method a function, which is evaluated on every
        cell of the TreeMesh.

        Occasionally it is useful to initially refine to a constant level
        (e.g. 3 in this 32x32 mesh). This means the function is first evaluated
        on an 8x8 mesh (2^3).

    """
    M = Mesh.TreeMesh([8, 8])

    def refine(cell):
        xyz = cell.center
        dist = ((xyz - [0.25, 0.25])**2).sum()**0.5
        if dist < 0.25:
            return 3
        return 2

    M.refine(refine)
    M.number()
    if plotIt:
        M.plotGrid(nodes=True, cells=True, facesX=True)
        plt.legend(('Grid', 'Cell Centers', 'Nodes', 'Hanging Nodes',
                    'X faces', 'Hanging X faces'))
Ejemplo n.º 4
0
def run(plotIt=True):
    """
        Mesh: QuadTree: Creation
        ========================

        You can give the refine method a function, which is evaluated on every
        cell of the TreeMesh.

        Occasionally it is useful to initially refine to a constant level
        (e.g. 3 in this 32x32 mesh). This means the function is first evaluated
        on an 8x8 mesh (2^3).

    """
    M = Mesh.TreeMesh([32, 32])
    M.refine(3)

    def refine(cell):
        xyz = cell.center
        for i in range(3):
            if np.abs(np.sin(xyz[0] * np.pi * 2) * 0.5 + 0.5 -
                      xyz[1]) < 0.2 * i:
                return 6 - i
        return 0

    M.refine(refine)
    if plotIt:
        M.plotGrid()
Ejemplo n.º 5
0
def run(plotIt=True):
    """
        Mesh: Basic: Types
        ==================

        Here we show SimPEG used to create three different types of meshes.

    """
    sz = [16, 16]
    tM = Mesh.TensorMesh(sz)
    qM = Mesh.TreeMesh(sz)
    qM.refine(lambda cell: 4
              if np.sqrt(((np.r_[cell.center] - 0.5)**2).sum()) < 0.4 else 3)
    rM = Mesh.CurvilinearMesh(Utils.meshutils.exampleLrmGrid(sz, 'rotate'))

    if plotIt:
        import matplotlib.pyplot as plt
        fig, axes = plt.subplots(1, 3, figsize=(14, 5))
        opts = {}
        tM.plotGrid(ax=axes[0], **opts)
        axes[0].set_title('TensorMesh')
        qM.plotGrid(ax=axes[1], **opts)
        axes[1].set_title('TreeMesh')
        rM.plotGrid(ax=axes[2], **opts)
        axes[2].set_title('CurvilinearMesh')
        plt.show()
Ejemplo n.º 6
0
 def test_refine(self):
     M = Mesh.TreeMesh([4, 4, 4])
     M.refine(1)
     assert M.nC == 8
     M.refine(0)
     assert M.nC == 8
     M.corsen(0)
     assert M.nC == 1
Ejemplo n.º 7
0
 def test_getitem(self):
     M = Mesh.TreeMesh([4, 4])
     M.refine(1)
     assert M.nC == 4
     assert len(M) == M.nC
     assert np.allclose(M[0].center, [0.25, 0.25])
     actual = [[0, 0], [0.5, 0], [0, 0.5], [0.5, 0.5]]
     for i, n in enumerate(M[0].nodes):
         assert np.allclose(M._gridN[n, :], actual[i])
Ejemplo n.º 8
0
    def test_VectorIdenties(self):
        hx, hy, hz = [[(1, 4)], [(1, 4)], [(1, 4)]]

        M = Mesh.TreeMesh([hx, hy, hz], levels=2)
        Mr = Mesh.TensorMesh([hx, hy, hz])

        assert (M.faceDiv * M.edgeCurl).nnz == 0
        assert (Mr.faceDiv * Mr.edgeCurl).nnz == 0

        hx, hy, hz = np.r_[1., 2, 3, 4], np.r_[5., 6, 7, 8], np.r_[9., 10, 11,
                                                                   12]

        M = Mesh.TreeMesh([hx, hy, hz], levels=2)
        Mr = Mesh.TensorMesh([hx, hy, hz])

        assert np.max(np.abs(
            (M.faceDiv * M.edgeCurl).todense().flatten())) < TOL
        assert np.max(np.abs(
            (Mr.faceDiv * Mr.edgeCurl).todense().flatten())) < TOL
Ejemplo n.º 9
0
    def test_edgeCurl(self):

        hx, hy, hz = np.r_[1., 2, 3, 4], np.r_[5., 6, 7, 8], np.r_[9., 10, 11,
                                                                   12]
        M = Mesh.TreeMesh([hx, hy, hz], levels=2)
        M.refine(lambda xc: 2)
        # M.plotGrid(showIt=True)
        Mr = Mesh.TensorMesh([hx, hy, hz])

        # plt.subplot(211).spy(Mr.faceDiv)
        # plt.subplot(212).spy(M.permuteCC.T*M.faceDiv*M.permuteF)
        # plt.show()

        assert (Mr.edgeCurl - M.permuteF * M.edgeCurl * M.permuteE.T).nnz == 0
Ejemplo n.º 10
0
def run(plotIt=True):
    M = Mesh.TreeMesh([32, 32])
    M.refine(3)

    def refine(cell):
        xyz = cell.center
        for i in range(3):
            if np.abs(np.sin(xyz[0]*np.pi*2)*0.5 + 0.5 - xyz[1]) < 0.2*i:
                return 6-i
        return 0

    M.refine(refine)
    if plotIt:
        M.plotGrid()
Ejemplo n.º 11
0
    def test_corsen(self):
        nc = 8
        h1 = np.random.rand(nc) * nc * 0.5 + nc * 0.5
        h2 = np.random.rand(nc) * nc * 0.5 + nc * 0.5
        h = [hi / np.sum(hi) for hi in [h1, h2]]  # normalize
        M = Mesh.TreeMesh(h)
        M._refineCell([0, 0, 0])
        M._refineCell([0, 0, 1])
        self.assertRaises(CellLookUpException, M._refineCell, [0, 0, 1])
        assert M._index([0, 0, 1]) not in M
        assert M._index([0, 0, 2]) in M
        assert M._index([2, 0, 2]) in M
        assert M._index([0, 2, 2]) in M
        assert M._index([2, 2, 2]) in M

        self.assertRaises(CellLookUpException, M._corsenCell, [0, 0, 1])
        M._corsenCell([0, 0, 2])
        assert M._index([0, 0, 1]) in M
        assert M._index([0, 0, 2]) not in M
        assert M._index([2, 0, 2]) not in M
        assert M._index([0, 2, 2]) not in M
        assert M._index([2, 2, 2]) not in M
        M._refineCell([0, 0, 1])

        self.assertRaises(CellLookUpException, M._corsenCell, [0, 0, 1])
        M._corsenCell([2, 0, 2])
        assert M._index([0, 0, 1]) in M
        assert M._index([0, 0, 2]) not in M
        assert M._index([2, 0, 2]) not in M
        assert M._index([0, 2, 2]) not in M
        assert M._index([2, 2, 2]) not in M
        M._refineCell([0, 0, 1])

        self.assertRaises(CellLookUpException, M._corsenCell, [0, 0, 1])
        M._corsenCell([0, 2, 2])
        assert M._index([0, 0, 1]) in M
        assert M._index([0, 0, 2]) not in M
        assert M._index([2, 0, 2]) not in M
        assert M._index([0, 2, 2]) not in M
        assert M._index([2, 2, 2]) not in M
        M._refineCell([0, 0, 1])

        self.assertRaises(CellLookUpException, M._corsenCell, [0, 0, 1])
        M._corsenCell([2, 2, 2])
        assert M._index([0, 0, 1]) in M
        assert M._index([0, 0, 2]) not in M
        assert M._index([2, 0, 2]) not in M
        assert M._index([0, 2, 2]) not in M
        assert M._index([2, 2, 2]) not in M
Ejemplo n.º 12
0
    def test_counts(self):
        nc = 8
        h1 = np.random.rand(nc) * nc * 0.5 + nc * 0.5
        h2 = np.random.rand(nc) * nc * 0.5 + nc * 0.5
        h3 = np.random.rand(nc) * nc * 0.5 + nc * 0.5
        h = [hi / np.sum(hi) for hi in [h1, h2, h3]]  # normalize
        M = Mesh.TreeMesh(h, levels=3)
        M._refineCell([0, 0, 0, 0])
        M._refineCell([0, 0, 0, 1])
        M.number()
        # M.plotGrid(showIt=True)
        # assert M.nhFx == 2
        # assert M.nFx == 9

        assert np.allclose(M.vol.sum(), 1.0)
Ejemplo n.º 13
0
    def setUp(self):
        def function(cell):
            r = cell.center - np.array([0.5] * len(cell.center))
            dist = np.sqrt(r.dot(r))
            if dist < 0.2:
                return 4
            if dist < 0.3:
                return 3
            if dist < 1.0:
                return 2
            else:
                return 0

        M = Mesh.TreeMesh([16, 16, 16], levels=4)
        M.refine(function)
        # M.plotGrid(showIt=True)
        self.M = M
Ejemplo n.º 14
0
def run(plotIt=True):
    """
        Mesh: Basic: PlotImage
        ======================

        You can use M.PlotImage to plot images on all of the Meshes.


    """
    M = Mesh.TensorMesh([32, 32])
    v = Utils.ModelBuilder.randomModel(M.vnC, seed=789)
    v = Utils.mkvc(v)

    O = Mesh.TreeMesh([32, 32])
    O.refine(1)

    def function(cell):
        if (cell.center[0] < 0.75 and cell.center[0] > 0.25
                and cell.center[1] < 0.75 and cell.center[1] > 0.25):
            return 5
        if (cell.center[0] < 0.9 and cell.center[0] > 0.1
                and cell.center[1] < 0.9 and cell.center[1] > 0.1):
            return 4
        return 3

    O.refine(function)

    P = M.getInterpolationMat(O.gridCC, 'CC')

    ov = P * v

    if not plotIt:
        return

    fig, axes = plt.subplots(1, 2, figsize=(10, 5))

    out = M.plotImage(v, grid=True, ax=axes[0])
    cb = plt.colorbar(out[0], ax=axes[0])
    cb.set_label("Random Field")
    axes[0].set_title('TensorMesh')

    out = O.plotImage(ov, grid=True, ax=axes[1], clim=[0, 1])
    cb = plt.colorbar(out[0], ax=axes[1])
    cb.set_label("Random Field")
    axes[1].set_title('TreeMesh')
Ejemplo n.º 15
0
    def test_counts(self):
        nc = 8
        h1 = np.random.rand(nc) * nc * 0.5 + nc * 0.5
        h2 = np.random.rand(nc) * nc * 0.5 + nc * 0.5
        h = [hi / np.sum(hi) for hi in [h1, h2]]  # normalize
        M = Mesh.TreeMesh(h)
        M._refineCell([0, 0, 0])
        M._refineCell([0, 0, 1])
        M.number()
        # M.plotGrid(showIt=True)
        print(M)
        assert M.nhFx == 2
        assert M.nFx == 9

        assert np.allclose(M.vol.sum(), 1.0)

        assert np.allclose(np.r_[M._areaFxFull, M._areaFyFull],
                           M._deflationMatrix('F') * M.area)
Ejemplo n.º 16
0
 def doTestFace(self, h, rep, fast, meshType, invProp=False, invMat=False):
     if meshType == 'Curv':
         hRect = Utils.exampleLrmGrid(h,'rotate')
         mesh = Mesh.CurvilinearMesh(hRect)
     elif meshType == 'Tree':
         mesh = Mesh.TreeMesh(h, levels=3)
         mesh.refine(lambda xc: 3)
         mesh.number(balance=False)
     elif meshType == 'Tensor':
         mesh = Mesh.TensorMesh(h)
     v = np.random.rand(mesh.nF)
     sig = np.random.rand(1) if rep is 0 else np.random.rand(mesh.nC*rep)
     def fun(sig):
         M  = mesh.getFaceInnerProduct(sig, invProp=invProp, invMat=invMat)
         Md = mesh.getFaceInnerProductDeriv(sig, invProp=invProp, invMat=invMat, doFast=fast)
         return M*v, Md(v)
     print meshType, 'Face', h, rep, fast, ('harmonic' if invProp and invMat else 'standard')
     return Tests.checkDerivative(fun, sig, num=5, plotIt=False)
def run(plotIt=True):
    M = Mesh.TreeMesh([8, 8])

    def refine(cell):
        xyz = cell.center
        dist = ((xyz - [0.25, 0.25])**2).sum()**0.5
        if dist < 0.25:
            return 3
        return 2

    M.refine(refine)
    M.number()
    if plotIt:
        M.plotGrid(nodes=True, cells=True, facesX=True)
        plt.legend((
            'Grid',
            'Cell Centers',
            'Nodes',
            'Hanging Nodes',
            'X faces',
            'Hanging X faces'
        ))
Ejemplo n.º 18
0
    def test_faceDiv(self):

        hx, hy = np.r_[1., 2, 3, 4], np.r_[5., 6, 7, 8]
        T = Mesh.TreeMesh([hx, hy], levels=2)
        T.refine(lambda xc: 2)
        # T.plotGrid(showIt=True)
        M = Mesh.TensorMesh([hx, hy])
        assert M.nC == T.nC
        assert M.nF == T.nF
        assert M.nFx == T.nFx
        assert M.nFy == T.nFy
        assert M.nE == T.nE
        assert M.nEx == T.nEx
        assert M.nEy == T.nEy
        assert np.allclose(M.area, T.permuteF * T.area)
        assert np.allclose(M.edge, T.permuteE * T.edge)
        assert np.allclose(M.vol, T.permuteCC * T.vol)

        # plt.subplot(211).spy(M.faceDiv)
        # plt.subplot(212).spy(T.permuteCC*T.faceDiv*T.permuteF.T)
        # plt.show()

        assert (M.faceDiv - T.permuteCC * T.faceDiv * T.permuteF.T).nnz == 0
Ejemplo n.º 19
0
def run(plotIt=True):
    sz = [16, 16]
    tM = Mesh.TensorMesh(sz)
    qM = Mesh.TreeMesh(sz)

    def refine(cell):
        if np.sqrt(((np.r_[cell.center] - 0.5)**2).sum()) < 0.4:
            return 4
        return 3

    qM.refine(refine)
    rM = Mesh.CurvilinearMesh(Utils.meshutils.exampleLrmGrid(sz, 'rotate'))

    if not plotIt:
        return
    fig, axes = plt.subplots(1, 3, figsize=(14, 5))
    opts = {}
    tM.plotGrid(ax=axes[0], **opts)
    axes[0].set_title('TensorMesh')
    qM.plotGrid(ax=axes[1], **opts)
    axes[1].set_title('TreeMesh')
    rM.plotGrid(ax=axes[2], **opts)
    axes[2].set_title('CurvilinearMesh')
Ejemplo n.º 20
0
    def test_faceInnerProduct(self):

        hx, hy, hz = np.r_[1., 2, 3, 4], np.r_[5., 6, 7, 8], np.r_[9., 10, 11,
                                                                   12]
        # hx, hy, hz = [[(1,4)], [(1,4)], [(1,4)]]

        M = Mesh.TreeMesh([hx, hy, hz], levels=2)
        M.refine(lambda xc: 2)
        # M.plotGrid(showIt=True)
        Mr = Mesh.TensorMesh([hx, hy, hz])

        # plt.subplot(211).spy(Mr.getFaceInnerProduct())
        # plt.subplot(212).spy(M.getFaceInnerProduct())
        # plt.show()

        # print(M.nC, M.nF, M.getFaceInnerProduct().shape, M.permuteF.shape)

        assert np.allclose(Mr.getFaceInnerProduct().todense(),
                           (M.permuteF * M.getFaceInnerProduct() *
                            M.permuteF.T).todense())
        assert np.allclose(Mr.getEdgeInnerProduct().todense(),
                           (M.permuteE * M.getEdgeInnerProduct() *
                            M.permuteE.T).todense())
Ejemplo n.º 21
0
    def test_faceDiv(self):

        hx, hy, hz = np.r_[1., 2, 3, 4], np.r_[5., 6, 7, 8], np.r_[9., 10, 11,
                                                                   12]
        M = Mesh.TreeMesh([hx, hy, hz], levels=2)
        M.refine(lambda xc: 2)
        # M.plotGrid(showIt=True)
        Mr = Mesh.TensorMesh([hx, hy, hz])
        assert M.nC == Mr.nC
        assert M.nF == Mr.nF
        assert M.nFx == Mr.nFx
        assert M.nFy == Mr.nFy
        assert M.nE == Mr.nE
        assert M.nEx == Mr.nEx
        assert M.nEy == Mr.nEy
        assert np.allclose(Mr.area, M.permuteF * M.area)
        assert np.allclose(Mr.edge, M.permuteE * M.edge)
        assert np.allclose(Mr.vol, M.permuteCC * M.vol)

        # plt.subplot(211).spy(Mr.faceDiv)
        # plt.subplot(212).spy(M.permuteCC*M.faceDiv*M.permuteF.T)
        # plt.show()

        assert (Mr.faceDiv - M.permuteCC * M.faceDiv * M.permuteF.T).nnz == 0
Ejemplo n.º 22
0
def plotVectorSectionsOctree(mesh,
                             m,
                             normal='X',
                             ind=0,
                             vmin=None,
                             vmax=None,
                             subFact=2,
                             scale=1.,
                             xlim=None,
                             ylim=None,
                             vec='k',
                             title=None,
                             axs=None,
                             actvMap=None,
                             contours=None,
                             fill=True,
                             orientation='vertical',
                             cmap='pink_r'):
    """
    Plot section through a 3D tensor model
    """
    # plot recovered model
    normalInd = {'X': 0, 'Y': 1, 'Z': 2}[normal]
    antiNormalInd = {'X': [1, 2], 'Y': [0, 2], 'Z': [0, 1]}[normal]

    h2d = (mesh.h[antiNormalInd[0]], mesh.h[antiNormalInd[1]])
    x2d = (mesh.x0[antiNormalInd[0]], mesh.x0[antiNormalInd[1]])

    #: Size of the sliced dimension
    szSliceDim = len(mesh.h[normalInd])
    if ind is None:
        ind = int(szSliceDim // 2)

    cc_tensor = [None, None, None]
    for i in range(3):
        cc_tensor[i] = np.cumsum(np.r_[mesh.x0[i], mesh.h[i]])
        cc_tensor[i] = (cc_tensor[i][1:] + cc_tensor[i][:-1]) * 0.5
    slice_loc = cc_tensor[normalInd][ind]

    # Create a temporary TreeMesh with the slice through
    temp_mesh = Mesh.TreeMesh(h2d, x2d)
    level_diff = mesh.max_level - temp_mesh.max_level

    XS = [None, None, None]
    XS[antiNormalInd[0]], XS[antiNormalInd[1]] = np.meshgrid(
        cc_tensor[antiNormalInd[0]], cc_tensor[antiNormalInd[1]])
    XS[normalInd] = np.ones_like(XS[antiNormalInd[0]]) * slice_loc
    loc_grid = np.c_[XS[0].reshape(-1), XS[1].reshape(-1), XS[2].reshape(-1)]
    inds = np.unique(mesh._get_containing_cell_indexes(loc_grid))

    grid2d = mesh.gridCC[inds][:, antiNormalInd]
    levels = mesh._cell_levels_by_indexes(inds) - level_diff
    temp_mesh.insert_cells(grid2d, levels)
    tm_gridboost = np.empty((temp_mesh.nC, 3))
    tm_gridboost[:, antiNormalInd] = temp_mesh.gridCC
    tm_gridboost[:, normalInd] = slice_loc

    # Interpolate values to mesh.gridCC if not 'CC'
    mx = (actvMap * m[:, 0])
    my = (actvMap * m[:, 1])
    mz = (actvMap * m[:, 2])

    m = np.c_[mx, my, mz]

    # Interpolate values from mesh.gridCC to grid2d
    ind_3d_to_2d = mesh._get_containing_cell_indexes(tm_gridboost)
    v2d = m[ind_3d_to_2d, :]
    amp = np.sum(v2d**2., axis=1)**0.5

    if axs is None:
        axs = plt.subplot(111)

    if fill:
        temp_mesh.plotImage(amp, ax=axs, clim=[vmin, vmax], grid=True)

    axs.quiver(temp_mesh.gridCC[:, 0],
               temp_mesh.gridCC[:, 1],
               v2d[:, antiNormalInd[0]],
               v2d[:, antiNormalInd[1]],
               pivot='mid',
               scale_units="inches",
               scale=scale,
               linewidths=(1, ),
               edgecolors=(vec),
               headaxislength=0.1,
               headwidth=10,
               headlength=30)
Ejemplo n.º 23
0
                      nCy * h[1] + padDist[1, :].sum(),
                      nCz * h[2] + padDist[2, :].sum()])

maxLevel = int(np.log2(extent / h[0])) + 1

# Number of cells at the small octree level
# For now equal in 3D

nCx, nCy, nCz = 2**(maxLevel), 2**(maxLevel), 2**(maxLevel)
# nCy = 2**(int(np.log2(extent/h[1]))+1)
# nCz = 2**(int(np.log2(extent/h[2]))+1)

# Define the mesh and origin
# For now cubic cells
mesh = Mesh.TreeMesh(
    [np.ones(nCx) * h[0],
     np.ones(nCx) * h[1],
     np.ones(nCx) * h[2]])

# Set origin
mesh.x0 = np.r_[-nCx * h[0] / 2. + midX, -nCy * h[1] / 2. + midY,
                -nCz * h[2] / 2. + midZ]

# mesh = Utils.modelutils.meshBuilder(topo, h, padDist,
#                                     meshType='TREE',
#                                     verticalAlignment='center')

# Refine the mesh around topography
# Get extent of points
F = NearestNDInterpolator(topo[:, :2], topo[:, 2])
zOffset = 0
# Cycle through the first 3 octree levels
Ejemplo n.º 24
0
def meshBuilder(xyz,
                h,
                padDist,
                meshGlobal=None,
                expFact=1.3,
                meshType='TENSOR',
                verticalAlignment='top'):
    """
        Function to quickly generate a Tensor mesh
        given a cloud of xyz points, finest core cell size
        and padding distance.
        If a meshGlobal is provided, the core cells will be centered
        on the underlaying mesh to reduce interpolation errors.

        :param numpy.ndarray xyz: n x 3 array of locations [x, y, z]
        :param numpy.ndarray h: 1 x 3 cell size for the core mesh
        :param numpy.ndarray padDist: 2 x 3 padding distances [W,E,S,N,Down,Up]
        [OPTIONAL]
        :param numpy.ndarray padCore: Number of core cells around the xyz locs
        :object SimPEG.Mesh: Base mesh used to shift the new mesh for overlap
        :param float expFact: Expension factor for padding cells [1.3]
        :param string meshType: Specify output mesh type: "TensorMesh"

        RETURNS:
        :object SimPEG.Mesh: Mesh object

    """

    assert meshType in ['TENSOR',
                        'TREE'], ('Revise meshType. Only ' +
                                  ' TENSOR | TREE mesh ' + 'are implemented')

    # Get extent of points
    limx = np.r_[xyz[:, 0].max(), xyz[:, 0].min()]
    limy = np.r_[xyz[:, 1].max(), xyz[:, 1].min()]
    limz = np.r_[xyz[:, 2].max(), xyz[:, 2].min()]

    # Get center of the mesh
    midX = np.mean(limx)
    midY = np.mean(limy)
    midZ = np.mean(limz)

    nCx = int(limx[0] - limx[1]) / h[0]
    nCy = int(limy[0] - limy[1]) / h[1]
    nCz = int(limz[0] - limz[1] + int(np.min(np.r_[nCx, nCy]) / 3)) / h[2]

    if meshType == 'TENSOR':
        # Make sure the core has odd number of cells for centereing
        # on global mesh
        if meshGlobal is not None:
            nCx += 1 - int(nCx % 2)
            nCy += 1 - int(nCy % 2)
            nCz += 1 - int(nCz % 2)

        # Figure out paddings
        def expand(dx, pad):
            L = 0
            nC = 0
            while L < pad:
                nC += 1
                L = np.sum(dx * expFact**(np.asarray(range(nC)) + 1))

            return nC

        # Figure number of padding cells required to fill the space
        npadEast = expand(h[0], padDist[0, 0])
        npadWest = expand(h[0], padDist[0, 1])
        npadSouth = expand(h[1], padDist[1, 0])
        npadNorth = expand(h[1], padDist[1, 1])
        npadDown = expand(h[2], padDist[2, 0])
        npadUp = expand(h[2], padDist[2, 1])

        # Create discretization
        hx = [(h[0], npadWest, -expFact), (h[0], nCx),
              (h[0], npadEast, expFact)]
        hy = [(h[1], npadSouth, -expFact), (h[1], nCy),
              (h[1], npadNorth, expFact)]
        hz = [(h[2], npadDown, -expFact), (h[2], nCz), (h[2], npadUp, expFact)]

        # Create mesh
        mesh = Mesh.TensorMesh([hx, hy, hz], 'CC0')

        # Re-set the mesh at the center of input locations
        # Set origin
        if verticalAlignment == 'center':
            mesh.x0 = [
                midX - np.sum(mesh.hx) / 2., midY - np.sum(mesh.hy) / 2.,
                midZ - np.sum(mesh.hz) / 2.
            ]
        elif verticalAlignment == 'top':
            mesh.x0 = [
                midX - np.sum(mesh.hx) / 2., midY - np.sum(mesh.hy) / 2.,
                limz[0] - np.sum(mesh.hz)
            ]
        else:
            assert NotImplementedError(
                "verticalAlignment must be 'center' | 'top'")

    elif meshType == 'TREE':

        # Figure out full extent required from input
        extent = np.max(np.r_[nCx * h[0] + padDist[0, :].sum(),
                              nCy * h[1] + padDist[1, :].sum(),
                              nCz * h[2] + padDist[2, :].sum()])

        maxLevel = int(np.log2(extent / h[0])) + 1

        # Number of cells at the small octree level
        # For now equal in 3D

        nCx, nCy, nCz = 2**(maxLevel), 2**(maxLevel), 2**(maxLevel)
        # nCy = 2**(int(np.log2(extent/h[1]))+1)
        # nCz = 2**(int(np.log2(extent/h[2]))+1)

        # Define the mesh and origin
        # For now cubic cells
        mesh = Mesh.TreeMesh(
            [np.ones(nCx) * h[0],
             np.ones(nCx) * h[1],
             np.ones(nCx) * h[2]])

        # Set origin
        if verticalAlignment == 'center':
            mesh.x0 = np.r_[-nCx * h[0] / 2. + midX, -nCy * h[1] / 2. + midY,
                            -nCz * h[2] / 2. + midZ]
        elif verticalAlignment == 'top':
            mesh.x0 = np.r_[-nCx * h[0] / 2. + midX, -nCy * h[1] / 2. + midY,
                            -(nCz - 1) * h[2] + limz.max()]
        else:
            assert NotImplementedError(
                "verticalAlignment must be 'center' | 'top'")

    return mesh
Ejemplo n.º 25
0
    def setUp(self):
        np.random.seed(0)
        H0 = (50000., 90., 0.)

        # The magnetization is set along a different
        # direction (induced + remanence)
        M = np.array([45., 90.])

        # Create grid of points for topography
        # Lets create a simple Gaussian topo
        # and set the active cells
        [xx, yy] = np.meshgrid(
            np.linspace(-200, 200, 50),
            np.linspace(-200, 200, 50)
        )
        b = 100
        A = 50
        zz = A*np.exp(-0.5*((xx/b)**2. + (yy/b)**2.))

        # We would usually load a topofile
        topo = np.c_[Utils.mkvc(xx), Utils.mkvc(yy), Utils.mkvc(zz)]

        # Create and array of observation points
        xr = np.linspace(-100., 100., 20)
        yr = np.linspace(-100., 100., 20)
        X, Y = np.meshgrid(xr, yr)
        Z = A*np.exp(-0.5*((X/b)**2. + (Y/b)**2.)) + 5

        # Create a MAGsurvey
        xyzLoc = np.c_[Utils.mkvc(X.T), Utils.mkvc(Y.T), Utils.mkvc(Z.T)]
        rxLoc = PF.BaseMag.RxObs(xyzLoc)
        srcField = PF.BaseMag.SrcField([rxLoc], param=H0)
        survey = PF.BaseMag.LinearSurvey(srcField)

        # Create a mesh
        h = [5, 5, 5]
        padDist = np.ones((3, 2)) * 100
        nCpad = [2, 4, 2]

        # Get extent of points
        limx = np.r_[topo[:, 0].max(), topo[:, 0].min()]
        limy = np.r_[topo[:, 1].max(), topo[:, 1].min()]
        limz = np.r_[topo[:, 2].max(), topo[:, 2].min()]

        # Get center of the mesh
        midX = np.mean(limx)
        midY = np.mean(limy)
        midZ = np.mean(limz)

        nCx = int(limx[0]-limx[1]) / h[0]
        nCy = int(limy[0]-limy[1]) / h[1]
        nCz = int(limz[0]-limz[1]+int(np.min(np.r_[nCx, nCy])/3)) / h[2]
        # Figure out full extent required from input
        extent = np.max(np.r_[nCx * h[0] + padDist[0, :].sum(),
                              nCy * h[1] + padDist[1, :].sum(),
                              nCz * h[2] + padDist[2, :].sum()])

        maxLevel = int(np.log2(extent/h[0]))+1

        # Number of cells at the small octree level
        nCx, nCy, nCz = 2**(maxLevel), 2**(maxLevel), 2**(maxLevel)

        # Define the mesh and origin
        # For now cubic cells
        mesh = Mesh.TreeMesh([np.ones(nCx)*h[0],
                              np.ones(nCx)*h[1],
                              np.ones(nCx)*h[2]])

        # Set origin
        mesh.x0 = np.r_[
            -nCx*h[0]/2.+midX,
            -nCy*h[1]/2.+midY,
            -nCz*h[2]/2.+midZ
        ]

        # Refine the mesh around topography
        # Get extent of points
        F = NearestNDInterpolator(topo[:, :2], topo[:, 2])
        zOffset = 0
        # Cycle through the first 3 octree levels
        for ii in range(3):

            dx = mesh.hx.min()*2**ii

            nCx = int((limx[0]-limx[1]) / dx)
            nCy = int((limy[0]-limy[1]) / dx)

            # Create a grid at the octree level in xy
            CCx, CCy = np.meshgrid(
                np.linspace(limx[1], limx[0], nCx),
                np.linspace(limy[1], limy[0], nCy)
            )

            z = F(mkvc(CCx), mkvc(CCy))

            # level means number of layers in current OcTree level
            for level in range(int(nCpad[ii])):

                mesh.insert_cells(
                    np.c_[
                        mkvc(CCx),
                        mkvc(CCy),
                        z-zOffset
                    ], np.ones_like(z)*maxLevel-ii,
                    finalize=False
                )

                zOffset += dx

        mesh.finalize()
        self.mesh = mesh
        # Define an active cells from topo
        actv = Utils.surface2ind_topo(mesh, topo)
        nC = int(actv.sum())

        model = np.zeros((mesh.nC, 3))

        # Convert the inclination declination to vector in Cartesian
        M_xyz = Utils.matutils.dip_azimuth2cartesian(M[0], M[1])

        # Get the indicies of the magnetized block
        ind = Utils.ModelBuilder.getIndicesBlock(
            np.r_[-20, -20, -10], np.r_[20, 20, 25],
            mesh.gridCC,
        )[0]

        # Assign magnetization values
        model[ind, :] = np.kron(
            np.ones((ind.shape[0], 1)), M_xyz*0.05
        )

        # Remove air cells
        self.model = model[actv, :]

        # Create active map to go from reduce set to full
        self.actvMap = Maps.InjectActiveCells(mesh, actv, np.nan)

        # Creat reduced identity map
        idenMap = Maps.IdentityMap(nP=nC*3)

        # Create the forward model operator
        prob = PF.Magnetics.MagneticIntegral(
            mesh, chiMap=idenMap, actInd=actv,
            modelType='vector'
        )

        # Pair the survey and problem
        survey.pair(prob)

        # Compute some data and add some random noise
        data = prob.fields(Utils.mkvc(self.model))
        std = 5  # nT
        data += np.random.randn(len(data))*std
        wd = np.ones(len(data))*std

        # Assigne data and uncertainties to the survey
        survey.dobs = data
        survey.std = wd

        # Create an projection matrix for plotting later
        actvPlot = Maps.InjectActiveCells(mesh, actv, np.nan)

        # Create sensitivity weights from our linear forward operator
        rxLoc = survey.srcField.rxList[0].locs

        # This Mapping connects the regularizations for the three-component
        # vector model
        wires = Maps.Wires(('p', nC), ('s', nC), ('t', nC))

        # Create sensitivity weights from our linear forward operator
        # so that all cells get equal chance to contribute to the solution
        wr = np.sum(prob.G**2., axis=0)**0.5
        wr = (wr/np.max(wr))

        # Create three regularization for the different components
        # of magnetization
        reg_p = Regularization.Sparse(mesh, indActive=actv, mapping=wires.p)
        reg_p.mref = np.zeros(3*nC)
        reg_p.cell_weights = (wires.p * wr)

        reg_s = Regularization.Sparse(mesh, indActive=actv, mapping=wires.s)
        reg_s.mref = np.zeros(3*nC)
        reg_s.cell_weights = (wires.s * wr)

        reg_t = Regularization.Sparse(mesh, indActive=actv, mapping=wires.t)
        reg_t.mref = np.zeros(3*nC)
        reg_t.cell_weights = (wires.t * wr)

        reg = reg_p + reg_s + reg_t
        reg.mref = np.zeros(3*nC)

        # Data misfit function
        dmis = DataMisfit.l2_DataMisfit(survey)
        dmis.W = 1./survey.std

        # Add directives to the inversion
        opt = Optimization.ProjectedGNCG(maxIter=30, lower=-10, upper=10.,
                                         maxIterLS=20, maxIterCG=20, tolCG=1e-4)

        invProb = InvProblem.BaseInvProblem(dmis, reg, opt)

        # A list of directive to control the inverson
        betaest = Directives.BetaEstimate_ByEig()

        # Here is where the norms are applied
        # Use pick a treshold parameter empirically based on the distribution of
        #  model parameters
        IRLS = Directives.Update_IRLS(
            f_min_change=1e-3, maxIRLSiter=0, beta_tol=5e-1
        )

        # Pre-conditioner
        update_Jacobi = Directives.UpdatePreconditioner()

        inv = Inversion.BaseInversion(invProb,
                                      directiveList=[IRLS, update_Jacobi, betaest])

        # Run the inversion
        m0 = np.ones(3*nC) * 1e-4  # Starting model
        mrec_MVIC = inv.run(m0)

        self.mstart = Utils.matutils.cartesian2spherical(mrec_MVIC.reshape((nC, 3), order='F'))
        beta = invProb.beta
        dmis.prob.coordinate_system = 'spherical'
        dmis.prob.model = self.mstart

        # Create a block diagonal regularization
        wires = Maps.Wires(('amp', nC), ('theta', nC), ('phi', nC))

        # Create a Combo Regularization
        # Regularize the amplitude of the vectors
        reg_a = Regularization.Sparse(mesh, indActive=actv,
                                      mapping=wires.amp)
        reg_a.norms = np.c_[0., 0., 0., 0.]  # Sparse on the model and its gradients
        reg_a.mref = np.zeros(3*nC)

        # Regularize the vertical angle of the vectors
        reg_t = Regularization.Sparse(mesh, indActive=actv,
                                      mapping=wires.theta)
        reg_t.alpha_s = 0.  # No reference angle
        reg_t.space = 'spherical'
        reg_t.norms = np.c_[2., 0., 0., 0.]  # Only norm on gradients used

        # Regularize the horizontal angle of the vectors
        reg_p = Regularization.Sparse(mesh, indActive=actv,
                                      mapping=wires.phi)
        reg_p.alpha_s = 0.  # No reference angle
        reg_p.space = 'spherical'
        reg_p.norms = np.c_[2., 0., 0., 0.]  # Only norm on gradients used

        reg = reg_a + reg_t + reg_p
        reg.mref = np.zeros(3*nC)

        Lbound = np.kron(np.asarray([0, -np.inf, -np.inf]), np.ones(nC))
        Ubound = np.kron(np.asarray([10, np.inf, np.inf]), np.ones(nC))

        # Add directives to the inversion
        opt = Optimization.ProjectedGNCG(maxIter=20,
                                         lower=Lbound,
                                         upper=Ubound,
                                         maxIterLS=20,
                                         maxIterCG=30,
                                         tolCG=1e-3,
                                         stepOffBoundsFact=1e-3,
                                         )
        opt.approxHinv = None

        invProb = InvProblem.BaseInvProblem(dmis, reg, opt, beta=beta*10.)

        # Here is where the norms are applied
        IRLS = Directives.Update_IRLS(f_min_change=1e-4, maxIRLSiter=20,
                                      minGNiter=1, beta_tol=0.5,
                                      coolingRate=1, coolEps_q=True,
                                      betaSearch=False)

        # Special directive specific to the mag amplitude problem. The sensitivity
        # weights are update between each iteration.
        ProjSpherical = Directives.ProjectSphericalBounds()
        update_SensWeight = Directives.UpdateSensitivityWeights()
        update_Jacobi = Directives.UpdatePreconditioner()

        self.inv = Inversion.BaseInversion(
            invProb,
            directiveList=[
                ProjSpherical, IRLS, update_SensWeight, update_Jacobi
            ]
        )
Ejemplo n.º 26
0
dh = 10  # minimum cell width (base mesh cell width)

dhx = 10
dhy = 1.5
dhz = dh

#Dimensao eixo vertical( base 2)
nbcx = 2**12  # number of base mesh cells in x
nbcy = 2**15
#nbcz =2**15
# Define base mesh (domain and finest discretization)
hx = dhx * np.ones(nbcx)
hy = dhy * np.ones(nbcy)
#hz = dhz*np.ones(nbcz)

M = Mesh.TreeMesh([hx, hy])

M.x0 = np.r_[-(nbcx * dhx) / 2, -nbcy * dhy + 15000]

#definir a camada

xp, yp = np.meshgrid([-(nbcx * dhx) / 2, (nbcx * dhx) / 2], [1., -1.])  #layer
xy = np.c_[mkvc(xp), mkvc(yp)]  # mkvc creates vectors

# Discretize to finest cell size within rectangular box
M = refine_tree_xyz(M, xy, octree_levels=[1, 1], method='box', finalize=False)

# Define objeto
xp, yp = np.meshgrid([-(nbcx * dhx) / 32, (nbcx * dhx) / 32],
                     [-10150, -10650.])  #goal
xy = np.c_[mkvc(xp), mkvc(yp)]  # mkvc creates vectors
Ejemplo n.º 27
0
def run(plotIt=True):

    nFreq = 13
    freqs = np.logspace(2, -2, nFreq)

    # x and y grid parameters
    #    dh = 10   # minimum cell width (base mesh cell width)

    dx = 15  # minimum cell width (base mesh cell width) in x
    dy = 15
    dz = 10

    x_length = 10000.  # domain width in x
    y_length = 10000.
    z_length = 40000.

    # Compute number of base mesh cells required in x and y
    nbcx = 2**int(np.round(np.log(x_length / dx) / np.log(2.)))
    nbcy = 2**int(np.round(np.log(y_length / dy) / np.log(2.)))
    nbcz = 2**int(np.round(np.log(z_length / dz) / np.log(2.)))

    # Define the base mesh
    hx = [(dx, nbcx)]
    hy = [(dy, nbcy)]
    hz = [(dz, nbcz)]

    M = Mesh.TreeMesh([hx, hy, hz], x0=['C', 'C', -15000])

    # camadas

    xx = M.vectorNx
    yy = M.vectorNy
    zz = np.zeros(nbcx + 1)  #vetor linha(poderia ser uma função ou pontos)
    pts = np.c_[matutils.mkvc(xx), matutils.mkvc(yy), matutils.mkvc(zz)]
    M = meshutils.refine_tree_xyz(M,
                                  pts,
                                  octree_levels=[1, 1, 1],
                                  method='surface',
                                  finalize=False)

    xx = M.vectorNx
    yy = M.vectorNy
    zz = np.zeros(nbcx +
                  1) - 150  #vetor linha(poderia ser uma função ou pontos)
    pts = np.c_[matutils.mkvc(xx), matutils.mkvc(yy), matutils.mkvc(zz)]
    M = meshutils.refine_tree_xyz(M,
                                  pts,
                                  octree_levels=[1, 1, 1],
                                  method='surface',
                                  finalize=False)

    xx = M.vectorNx
    yy = M.vectorNy
    zz = np.zeros(nbcx +
                  1) - 350  #vetor linha(poderia ser uma função ou pontos)
    pts = np.c_[matutils.mkvc(xx), matutils.mkvc(yy), matutils.mkvc(zz)]
    M = meshutils.refine_tree_xyz(M,
                                  pts,
                                  octree_levels=[1, 1, 1],
                                  method='surface',
                                  finalize=False)

    #
    M.finalize()
    print("\n the mesh has {} cells".format(M))

    ccMesh = M.gridCC
    print('indices:', np.size(ccMesh))
    ###

    conds = [1e-2, 1]
    sig = simpeg.Utils.ModelBuilder.defineBlock(M.gridCC,
                                                [-15000, 15000, -350],
                                                [15000, 1500, -150], conds)

    sig[M.gridCC[:, 2] > 0] = 1e-8
    sigBG = np.zeros(M.nC) + conds[1]
    sigBG[M.gridCC[:, 2] > 0] = 1e-8

    fig = plt.figure('slice: malha + modelo')
    ax = fig.add_subplot()
    collect_obj, = M.plotSlice(np.log(sig), normal='x', ax=ax, grid=True)
Ejemplo n.º 28
0
    def test_vs_mesh_vs_loguniform(self):
        """
        Test to make sure OcTree matches Tensor results and linear vs
        loguniform match
        """

        h1 = [(2, 4)]
        h2 = 0.5 * np.ones(16)
        meshObj_Tensor = Mesh.TensorMesh((h1, h1, h1), x0='000')
        meshObj_OcTree = Mesh.TreeMesh([h2, h2, h2], x0='000')

        x, y, z = np.meshgrid(np.c_[1., 3., 5., 7.], np.c_[1., 3., 5., 7.],
                              np.c_[1., 3., 5., 7.])
        x = x.reshape((4**3, 1))
        y = y.reshape((4**3, 1))
        z = z.reshape((4**3, 1))
        loc_rx = np.c_[x, y, z]
        meshObj_OcTree.insert_cells(loc_rx,
                                    2 * np.ones((4**3)),
                                    finalize=False)

        x, y, z = np.meshgrid(np.c_[1., 3., 5., 7.], np.c_[1., 3., 5., 7.],
                              np.c_[5., 7.])
        x = x.reshape((32, 1))
        y = y.reshape((32, 1))
        z = z.reshape((32, 1))
        loc_rx = np.c_[x, y, z]
        meshObj_OcTree.insert_cells(loc_rx, 3 * np.ones((32)), finalize=False)

        x, y, z = np.meshgrid(np.c_[3.5, 4.0, 4.5, 5.0, 5.5],
                              np.c_[3.5, 4.0, 4.5, 5.0, 5.5], np.c_[6.0, 6.5,
                                                                    7.0, 7.5])
        x = x.reshape((100, 1))
        y = y.reshape((100, 1))
        z = z.reshape((100, 1))
        loc_rx = np.c_[x, y, z]
        meshObj_OcTree.insert_cells(loc_rx, 4 * np.ones((100)), finalize=True)

        chi0 = 0.
        dchi = 0.01
        tau1 = 1e-8
        tau2 = 1e0

        # Tensor Models
        mod_a = (dchi / np.log(tau2 / tau1)) * np.ones(meshObj_Tensor.nC)
        mod_chi0_a = chi0 * np.ones(meshObj_Tensor.nC)
        mod_dchi_a = dchi * np.ones(meshObj_Tensor.nC)
        mod_tau1_a = tau1 * np.ones(meshObj_Tensor.nC)
        mod_tau2_a = tau2 * np.ones(meshObj_Tensor.nC)

        # OcTree Models
        mod_b = (dchi / np.log(tau2 / tau1)) * np.ones(meshObj_OcTree.nC)
        mod_chi0_b = chi0 * np.ones(meshObj_OcTree.nC)
        mod_dchi_b = dchi * np.ones(meshObj_OcTree.nC)
        mod_tau1_b = tau1 * np.ones(meshObj_OcTree.nC)
        mod_tau2_b = tau2 * np.ones(meshObj_OcTree.nC)

        times = np.array([1e-3])
        waveObj = VRM.WaveformVRM.SquarePulse(delt=0.02)

        loc_rx = np.c_[4., 4., 8.25]
        rxList = [
            VRM.Rx.Point(loc_rx, times=times, fieldType='dhdt', fieldComp='z')
        ]
        txList = [
            VRM.Src.MagDipole(rxList, np.r_[4., 4., 8.25], [0., 0., 1.],
                              waveObj)
        ]

        Survey1 = VRM.Survey(txList)
        Survey2 = VRM.Survey(txList)
        Survey3 = VRM.Survey(txList)
        Survey4 = VRM.Survey(txList)
        Problem1 = VRM.Problem_Linear(meshObj_Tensor,
                                      ref_factor=2,
                                      ref_radius=[1.9, 3.6])
        Problem2 = VRM.Problem_LogUniform(meshObj_Tensor,
                                          ref_factor=2,
                                          ref_radius=[1.9, 3.6],
                                          chi0=mod_chi0_a,
                                          dchi=mod_dchi_a,
                                          tau1=mod_tau1_a,
                                          tau2=mod_tau2_a)
        Problem3 = VRM.Problem_Linear(meshObj_OcTree, ref_factor=0)
        Problem4 = VRM.Problem_LogUniform(meshObj_OcTree,
                                          ref_factor=0,
                                          chi0=mod_chi0_b,
                                          dchi=mod_dchi_b,
                                          tau1=mod_tau1_b,
                                          tau2=mod_tau2_b)
        Problem1.pair(Survey1)
        Problem2.pair(Survey2)
        Problem3.pair(Survey3)
        Problem4.pair(Survey4)
        Fields1 = Problem1.fields(mod_a)
        Fields2 = Problem2.fields()
        Fields3 = Problem3.fields(mod_b)
        Fields4 = Problem4.fields()
        dpred1 = Survey1.dpred(mod_a)
        dpred2 = Survey2.dpred(mod_a)

        Err1 = np.abs((Fields1 - Fields2) / Fields1)
        Err2 = np.abs((Fields2 - Fields3) / Fields2)
        Err3 = np.abs((Fields3 - Fields4) / Fields3)
        Err4 = np.abs((Fields4 - Fields1) / Fields4)
        Err5 = np.abs((dpred1 - dpred2) / dpred1)

        Test1 = Err1 < 0.01
        Test2 = Err2 < 0.01
        Test3 = Err3 < 0.01
        Test4 = Err4 < 0.01
        Test5 = Err5 < 0.01

        self.assertTrue(Test1 and Test2 and Test3 and Test4 and Test5)
Ejemplo n.º 29
0
    def setUp(self):
        # We will assume a vertical inducing field
        H0 = (50000., 90., 0.)

        # The magnetization is set along a different direction (induced + remanence)
        M = np.array([90., 0.])

        # Block with an effective susceptibility
        chi_e = 0.05

        # Create grid of points for topography
        # Lets create a simple Gaussian topo and set the active cells
        [xx, yy] = np.meshgrid(np.linspace(-200, 200, 50),
                               np.linspace(-200, 200, 50))
        b = 100
        A = 50
        zz = A * np.exp(-0.5 * ((xx / b)**2. + (yy / b)**2.))
        topo = np.c_[Utils.mkvc(xx), Utils.mkvc(yy), Utils.mkvc(zz)]

        # Create and array of observation points
        xr = np.linspace(-100., 100., 20)
        yr = np.linspace(-100., 100., 20)
        X, Y = np.meshgrid(xr, yr)
        Z = A * np.exp(-0.5 * ((X / b)**2. + (Y / b)**2.)) + 5

        # Create a MAGsurvey
        rxLoc = np.c_[Utils.mkvc(X.T), Utils.mkvc(Y.T), Utils.mkvc(Z.T)]
        Rx = PF.BaseMag.RxObs(rxLoc)
        srcField = PF.BaseMag.SrcField([Rx], param=H0)
        survey = PF.BaseMag.LinearSurvey(srcField)

        # Create a mesh
        h = [5, 5, 5]
        padDist = np.ones((3, 2)) * 100
        nCpad = [4, 4, 2]

        # Get extent of points
        limx = np.r_[topo[:, 0].max(), topo[:, 0].min()]
        limy = np.r_[topo[:, 1].max(), topo[:, 1].min()]
        limz = np.r_[topo[:, 2].max(), topo[:, 2].min()]

        # Get center of the mesh
        midX = np.mean(limx)
        midY = np.mean(limy)
        midZ = np.mean(limz)

        nCx = int(limx[0] - limx[1]) / h[0]
        nCy = int(limy[0] - limy[1]) / h[1]
        nCz = int(limz[0] - limz[1] + int(np.min(np.r_[nCx, nCy]) / 3)) / h[2]

        # Figure out full extent required from input
        extent = np.max(np.r_[nCx * h[0] + padDist[0, :].sum(),
                              nCy * h[1] + padDist[1, :].sum(),
                              nCz * h[2] + padDist[2, :].sum()])

        maxLevel = int(np.log2(extent / h[0])) + 1

        # Number of cells at the small octree level
        # For now equal in 3D
        nCx, nCy, nCz = 2**(maxLevel), 2**(maxLevel), 2**(maxLevel)

        # Define the mesh and origin
        mesh = Mesh.TreeMesh(
            [np.ones(nCx) * h[0],
             np.ones(nCx) * h[1],
             np.ones(nCx) * h[2]])

        # Set origin
        mesh.x0 = np.r_[-nCx * h[0] / 2. + midX, -nCy * h[1] / 2. + midY,
                        -nCz * h[2] / 2. + midZ]

        # Refine the mesh around topography
        # Get extent of points
        F = NearestNDInterpolator(topo[:, :2], topo[:, 2])
        zOffset = 0
        # Cycle through the first 3 octree levels
        for ii in range(3):

            dx = mesh.hx.min() * 2**ii

            nCx = int((limx[0] - limx[1]) / dx)
            nCy = int((limy[0] - limy[1]) / dx)

            # Create a grid at the octree level in xy
            CCx, CCy = np.meshgrid(np.linspace(limx[1], limx[0], nCx),
                                   np.linspace(limy[1], limy[0], nCy))

            z = F(mkvc(CCx), mkvc(CCy))

            # level means number of layers in current OcTree level
            for level in range(int(nCpad[ii])):

                mesh.insert_cells(np.c_[mkvc(CCx),
                                        mkvc(CCy), z - zOffset],
                                  np.ones_like(z) * maxLevel - ii,
                                  finalize=False)

                zOffset += dx

        mesh.finalize()

        # Define an active cells from topo
        actv = Utils.surface2ind_topo(mesh, topo)
        nC = int(actv.sum())

        # Convert the inclination declination to vector in Cartesian
        M_xyz = Utils.matutils.dip_azimuth2cartesian(
            np.ones(nC) * M[0],
            np.ones(nC) * M[1])

        # Get the indicies of the magnetized block
        ind = Utils.ModelBuilder.getIndicesBlock(
            np.r_[-20, -20, -10],
            np.r_[20, 20, 25],
            mesh.gridCC,
        )[0]

        # Assign magnetization value, inducing field strength will
        # be applied in by the :class:`SimPEG.PF.Magnetics` problem
        model = np.zeros(mesh.nC)
        model[ind] = chi_e

        # Remove air cells
        self.model = model[actv]

        # Create active map to go from reduce set to full
        self.actvPlot = Maps.InjectActiveCells(mesh, actv, np.nan)

        # Creat reduced identity map
        idenMap = Maps.IdentityMap(nP=nC)

        # Create the forward model operator
        prob = PF.Magnetics.MagneticIntegral(mesh,
                                             M=M_xyz,
                                             chiMap=idenMap,
                                             actInd=actv)

        # Pair the survey and problem
        survey.pair(prob)

        # Compute some data and add some random noise
        data = prob.fields(self.model)

        # Split the data in components
        nD = rxLoc.shape[0]

        std = 5  # nT
        data += np.random.randn(nD) * std
        wd = np.ones(nD) * std

        # Assigne data and uncertainties to the survey
        survey.dobs = data
        survey.std = wd

        ######################################################################
        # Equivalent Source

        # Get the active cells for equivalent source is the top only
        surf = Utils.modelutils.surface_layer_index(mesh, topo)

        # Get the layer of cells directyl below topo
        nC = np.count_nonzero(surf)  # Number of active cells

        # Create active map to go from reduce set to full
        surfMap = Maps.InjectActiveCells(mesh, surf, np.nan)

        # Create identity map
        idenMap = Maps.IdentityMap(nP=nC)

        # Create static map
        prob = PF.Magnetics.MagneticIntegral(mesh,
                                             chiMap=idenMap,
                                             actInd=surf,
                                             parallelized=False,
                                             equiSourceLayer=True)

        prob.solverOpts['accuracyTol'] = 1e-4

        # Pair the survey and problem
        if survey.ispaired:
            survey.unpair()
        survey.pair(prob)

        # Create a regularization function, in this case l2l2
        reg = Regularization.Sparse(mesh,
                                    indActive=surf,
                                    mapping=Maps.IdentityMap(nP=nC),
                                    scaledIRLS=False)
        reg.mref = np.zeros(nC)

        # Specify how the optimization will proceed,
        # set susceptibility bounds to inf
        opt = Optimization.ProjectedGNCG(maxIter=20,
                                         lower=-np.inf,
                                         upper=np.inf,
                                         maxIterLS=20,
                                         maxIterCG=20,
                                         tolCG=1e-3)

        # Define misfit function (obs-calc)
        dmis = DataMisfit.l2_DataMisfit(survey)
        dmis.W = 1. / survey.std

        # Create the default L2 inverse problem from the above objects
        invProb = InvProblem.BaseInvProblem(dmis, reg, opt)

        # Specify how the initial beta is found
        betaest = Directives.BetaEstimate_ByEig()

        # Target misfit to stop the inversion,
        # try to fit as much as possible of the signal,
        # we don't want to lose anything
        IRLS = Directives.Update_IRLS(f_min_change=1e-3,
                                      minGNiter=1,
                                      beta_tol=1e-1)
        update_Jacobi = Directives.UpdatePreconditioner()
        # Put all the parts together
        inv = Inversion.BaseInversion(
            invProb, directiveList=[betaest, IRLS, update_Jacobi])

        # Run the equivalent source inversion
        mstart = np.ones(nC) * 1e-4
        mrec = inv.run(mstart)

        # Won't store the sensitivity and output 'xyz' data.
        prob.forwardOnly = True
        prob.rx_type = 'xyz'
        prob._G = None
        prob.modelType = 'amplitude'
        prob.model = mrec
        pred = prob.fields(mrec)

        bx = pred[:nD]
        by = pred[nD:2 * nD]
        bz = pred[2 * nD:]

        bAmp = (bx**2. + by**2. + bz**2.)**0.5

        # AMPLITUDE INVERSION
        # Create active map to go from reduce space to full
        actvMap = Maps.InjectActiveCells(mesh, actv, -100)
        nC = int(actv.sum())

        # Create identity map
        idenMap = Maps.IdentityMap(nP=nC)

        self.mstart = np.ones(nC) * 1e-4

        # Create the forward model operator
        prob = PF.Magnetics.MagneticIntegral(mesh,
                                             chiMap=idenMap,
                                             actInd=actv,
                                             modelType='amplitude',
                                             rx_type='xyz')
        prob.model = self.mstart
        # Change the survey to xyz components
        surveyAmp = PF.BaseMag.LinearSurvey(survey.srcField)

        # Pair the survey and problem
        surveyAmp.pair(prob)
        # Create a regularization function, in this case l2l2
        wr = np.sum(prob.G**2., axis=0)**0.5
        wr = (wr / np.max(wr))
        # Re-set the observations to |B|
        surveyAmp.dobs = bAmp
        surveyAmp.std = wd

        # Create a sparse regularization
        reg = Regularization.Sparse(mesh, indActive=actv, mapping=idenMap)
        reg.norms = np.c_[0, 0, 0, 0]
        reg.mref = np.zeros(nC)
        reg.cell_weights = wr
        # Data misfit function
        dmis = DataMisfit.l2_DataMisfit(surveyAmp)
        dmis.W = 1. / surveyAmp.std

        # Add directives to the inversion
        opt = Optimization.ProjectedGNCG(maxIter=30,
                                         lower=0.,
                                         upper=1.,
                                         maxIterLS=20,
                                         maxIterCG=20,
                                         tolCG=1e-3)

        invProb = InvProblem.BaseInvProblem(dmis, reg, opt)

        # Here is the list of directives
        betaest = Directives.BetaEstimate_ByEig()

        # Specify the sparse norms
        IRLS = Directives.Update_IRLS(f_min_change=1e-3,
                                      minGNiter=1,
                                      coolingRate=1,
                                      betaSearch=False)

        # The sensitivity weights are update between each iteration.
        update_SensWeight = Directives.UpdateSensitivityWeights()
        update_Jacobi = Directives.UpdatePreconditioner(threshold=1 - 3)

        # Put all together
        self.inv = Inversion.BaseInversion(
            invProb,
            directiveList=[betaest, IRLS, update_SensWeight, update_Jacobi])

        self.mesh = mesh
def run(plotIt=True):

    nFreq = 13
    freqs = np.logspace(2, -2, nFreq)

    # x and y grid parameters
    dh = 10  # minimum cell width (base mesh cell width)

    dhx = dh
    dhy = dh
    dhz = 1.5

    #Dimensao eixo vertical( base 2)
    nbcx = 2**12  # number of base mesh cells in x
    nbcy = 2**12
    nbcz = 2**15
    # Define base mesh (domain and finest discretization)
    hx = dhx * np.ones(nbcx)
    hy = dhy * np.ones(nbcy)
    hz = dhz * np.ones(nbcz)

    M = Mesh.TreeMesh([hx, hy, hz])
    #M.x0 = np.r_[-(nbcx*dhx)/2,-(nbcy*dhy)/2,-(nbcz*dhz)/2]
    M.x0 = np.r_[-(nbcx * dhx) / 2, -(nbcy * dhy) / 2, -nbcz * dhz + 15000]

    hz = [0]  # definir fronteira das camadas
    n_camadas = len(hz)

    #=========================================
    #Criando mais uma área(layer) de dricretização
    #=========================================

    for i in range(0, n_camadas, 1):
        xp, yp, zp = np.meshgrid([-(nbcx * dhx) / 1, (nbcx * dhx) / 1],
                                 [-(nbcy * dhy) / 1,
                                  (nbcy * dhy) / 1], [hz[i] - 1, hz[i] + 1])
        xyz = np.c_[mkvc(xp), mkvc(yp), mkvc(zp)]  # mkvc creates vectors
        M = refine_tree_xyz(M,
                            xyz,
                            octree_levels=[0, 0, 1],
                            method='radial',
                            finalize=False)

#=========================================
#Criando um objeto(target)
#=========================================

    xp, yp, zp = np.meshgrid([-(nbcx * dhx) / 32, (nbcx * dhx) / 32],
                             [-(nbcy * dhy) / 32,
                              (nbcy * dhy) / 32], [-150, -350])
    xyz = np.c_[mkvc(xp), mkvc(yp), mkvc(zp)]
    #refino
    M = refine_tree_xyz(M,
                        xyz,
                        octree_levels=[1, 1, 1],
                        method='box',
                        finalize=False)

    #
    M.finalize()
    print("\n the mesh has {} cells".format(M))

    ccMesh = M.gridCC
    print('indices:', np.size(ccMesh))
    ##
    ##
    ##
    ##
    conds = [1e-2, 1]
    sig = simpeg.Utils.ModelBuilder.defineBlock(M.gridCC,
                                                [-20000, -20000, -350],
                                                [20000, 20000, -150], conds)

    sig[M.gridCC[:, 2] > 0] = 1e-8
    sigBG = np.zeros(M.nC) + conds[1]
    sigBG[M.gridCC[:, 2] > 0] = 1e-8
    #

    # A boolean array specifying which cells lie on the boundary
    bInd = M.cellBoundaryInd

    ##   Cell volumes
    v = M.vol

    fig = plt.figure()
    ax = fig.add_subplot(111)
    collect_obj, = M.plotSlice(np.log10(sig), normal='x', ax=ax, grid=True)
    plt.colorbar(collect_obj)
    ax.set_title('slice')