Beispiel #1
0
def sampling_error():
    """
    Test the sampling error by comparing the accuracy of the quantities of 
    interest q1 = E[|y|] and q2 = E[y(0.5)]
        
    """
    c = Verbose()
    mesh = Mesh1D(resolution=(1026,))
    mesh.mark_region('left', lambda x:np.abs(x)<1e-10)
    mesh.mark_region('right', lambda x:np.abs(x-1)<1e-10)
    
    element = QuadFE(1,'Q1')
    dofhandler = DofHandler(mesh, element)
    dofhandler.distribute_dofs()
    dofhandler.set_dof_vertices()
    
    phi = Basis(dofhandler,'u')
    phi_x = Basis(dofhandler,'ux')
    
    ns_ref = 10000
    z = get_points(n_samples=ns_ref)
    q = set_diffusion(dofhandler,z)
    
    problems = [[Form(q, test=phi_x, trial=phi_x), Form(1, test=phi)],
                [Form(1, test=phi, trial=phi)]]
    
    c.tic('assembling')
    assembler = Assembler(problems, mesh)
    assembler.assemble()
    c.toc()
    
    A = assembler.af[0]['bilinear'].get_matrix()
    b = assembler.af[0]['linear'].get_matrix()
    M = assembler.af[0]['bilinear'].get_matrix()
    
    system = LS(phi)
    system.add_dirichlet_constraint('left')
    system.add_dirichlet_constraint('right')
    
    c.tic('solving')
    for n in range(ns_ref):
        system.set_matrix(A[n])
        system.set_rhs(b.copy())    
        system.solve_system()
        
    c.toc()    
Beispiel #2
0
mesh = Mesh1D(box=[x_min, x_max], resolution=(256, ))

# Mark Dirichlet Vertices
mesh.mark_region('left', lambda x: np.abs(x) < 1e-9)
mesh.mark_region('right', lambda x: np.abs(x - 2) < 1e-9)

#
# Finite element spaces
#
Q1 = QuadFE(mesh.dim(), 'Q1')

# Dofhandler for state
dh = DofHandler(mesh, Q1)
dh.distribute_dofs()
m = dh.n_dofs()
dh.set_dof_vertices()
x = dh.get_dof_vertices()

# Basis functions
phi = Basis(dh, 'v')
phi_x = Basis(dh, 'vx')

state = LS(phi)
state.add_dirichlet_constraint('left', 1)
state.add_dirichlet_constraint('right', 0)
state.set_constraint_relation()

adjoint = LS(phi)
adjoint.add_dirichlet_constraint('left', 0)
adjoint.add_dirichlet_constraint('right', 0)
adjoint.set_constraint_relation()
Beispiel #3
0
    def test_set_hanging_nodes(self):
        """
        Check that functions in the finite element space can be interpolated
        by linear combinations of shape functions at supporting nodes.
        
        TODO: Move this test to tests for system
        """        
        #
        # Define QuadMesh with hanging node
        # 
        mesh = QuadMesh(resolution=(1,1))        
        mesh.cells.refine()
        mesh.cells.get_child(0).get_child(0).mark(flag=0)                
        mesh.cells.refine(refinement_flag=0)
        
        c_00 = mesh.cells.get_child(0).get_child(0)
        #
        # Define test functions to interpolate
        # 
        test_functions = {'Q1': lambda x,y: x + y, \
                          'Q2': lambda x,y: x**2 + y**2,\
                          'Q3': lambda x,y: x**3*y + y**2*x**2}
        etypes = ['Q1', 'Q2', 'Q3']
        plot = Plot()
        for etype in etypes:
            #print(etype)
            # Define new element
            element = QuadFE(2,etype)
        
            # Distribute dofs and set vertices
            dofhandler = DofHandler(mesh, element)
            dofhandler.distribute_dofs()
            dofhandler.set_dof_vertices()
            
            # Determine hanging nodes
            dofhandler.set_hanging_nodes()
            hanging_nodes = dofhandler.get_hanging_nodes()
            for dof, support in hanging_nodes.items():
                # Get hanging node vertex
                x_hgnd = dofhandler.get_dof_vertices(dof)

                # Extract support indices and weights
                js, ws = support 
                
                # Extract
                dofs_glb = dofhandler.get_cell_dofs(c_00)
                
                #print(dof, js)
                
                # Local dof numbers for supporting nodes
                dofs_loc_supp = [i for i in range(element.n_dofs()) if dofs_glb[i] in js]
                #x_dofs = c_00.reference_map(element.reference_nodes())
                
                #phi_supp = element.shape(x_hgnd, cell=c_00, local_dofs=dofs_loc_supp)
                #print(phi_supp, js)
                
                # Evaluate test function at hanging node 
                #f_hgnd = test_functions[etype](x_hgnd[0],x_hgnd[1])

                #print('Weighted sum of support function', np.dot(phi_supp,ws))
                
                #print(f_hgnd - np.dot(phi_supp, ws))
                #phi_hgnd = element.shape(x_dofs, cell=c_00, local_dofs=dofs_loc_hgnd)
                
                #print(phi_supp)
                #print(phi_hgnd)
            #plot.mesh(mesh, dofhandler=dofhandler, dofs=True)
            
            # Evaluate 
            c_01 = mesh.cells.get_child(0).get_child(1)
            c_022 = mesh.cells.get_child(0).get_child(2).get_child(2)
            #print(dofhandler.get_global_dofs(c_022))
            x_ref = element.reference_nodes()
            #print(dofhandler.get_global_dofs(c_01))
            #print(dofhandler.get_hanging_nodes())
            x = c_01.reference_map(x_ref)
Beispiel #4
0
    def test_set_data(self):
        meshes = {1: Mesh1D(), 2: QuadMesh()}
        elements = {1: QuadFE(1, 'Q2'), 2: QuadFE(2, 'Q2')}

        #
        # Use function to set data
        #
        fns = {
            1: {
                1: lambda x: 2 * x[:, 0]**2,
                2: lambda x, y: 2 * x[:, 0] + 2 * y[:, 0]
            },
            2: {
                1: lambda x: x[:, 0]**2 + x[:, 1],
                2: lambda x, y: x[:, 0] * y[:, 0] + x[:, 1] * y[:, 1]
            }
        }

        parms = {1: {1: [{}, {}], 2: [{}, {}]}, 2: {1: [{}, {}], 2: [{}, {}]}}

        for dim in [1, 2]:
            # Get mesh and element
            mesh = meshes[dim]
            element = elements[dim]

            # Set dofhandler
            dofhandler = DofHandler(mesh, element)
            dofhandler.distribute_dofs()
            n_dofs = dofhandler.n_dofs()

            # Set basis
            basis = Basis(dofhandler)

            # Determine the shapes of the data
            det_shapes = {1: (n_dofs, 1), 2: (n_dofs, n_dofs, 1)}
            smp_shapes = {1: (n_dofs, 2), 2: (n_dofs, n_dofs, 2)}

            # Get a vertex
            i = np.random.randint(n_dofs)
            j = np.random.randint(n_dofs)
            dofhandler.set_dof_vertices()
            x = dofhandler.get_dof_vertices()

            x1 = np.array([x[i, :]])
            x2 = np.array([x[j, :]])

            for n_variables in [1, 2]:
                fn = fns[dim][n_variables]
                parm = parms[dim][n_variables]
                #
                # Deterministic
                #
                f = Nodal(f=fn, basis=basis, n_variables=n_variables)

                # Check shape
                self.assertEqual(f.data().shape, det_shapes[n_variables])

                # Check value
                if n_variables == 1:
                    val = fn(x1)[0]
                    self.assertEqual(val, f.data()[i])
                else:
                    val = fn(x1, x2)
                    self.assertEqual(val[0], f.data()[i, j])

                #
                # Sampled
                #
                f = Nodal(f=fn,
                          parameters=parm,
                          basis=basis,
                          n_variables=n_variables)

                # Check shape
                self.assertEqual(f.data().shape, smp_shapes[n_variables])

                # Check that samples are stored in the right place
                if n_variables == 1:
                    self.assertTrue(np.allclose(f.data()[:, 0],
                                                f.data()[:, 1]))
                elif n_variables == 2:
                    self.assertTrue(
                        np.allclose(f.data()[:, :, 0],
                                    f.data()[:, :, 1]))
Beispiel #5
0
    def test_constructor(self):
        # =====================================================================
        # Test 1D 
        # ===================================================================== 
        
        #
        # Kernel consists of a single explicit Function: 
        # 
        f1 = lambda x: x+2
        f = Explicit(f1, dim=1)
        k = Kernel(f)
        x = np.linspace(0,1,100)
        n_points = len(x)
        
        # Check that it evaluates correctly.
        self.assertTrue(np.allclose(f1(x), k.eval(x).ravel()))
        
        # Check shape of kernel
        self.assertEqual(k.eval(x).shape, (n_points,1))
        
        #
        # Kernel consists of a combination of two explicit functions
        # 
        f1 = Explicit(lambda x: x+2, dim=1)
        f2 = Explicit(lambda x: x**2 + 1, dim=1)
        F = lambda f1, f2: f1**2 + f2
        f_t = lambda x: (x+2)**2 + x**2 + 1
        k = Kernel([f1,f2], F=F)
        
        # Check evaluation
        self.assertTrue(np.allclose(f_t(x), k.eval(x).ravel()))
        
        # Check shape 
        self.assertEqual(k.eval(x).shape, (n_points,1))
        

        #
        # Same thing as above, but with nodal functions
        # 
        mesh = Mesh1D(resolution=(1,))
        Q1 = QuadFE(1,'Q1')
        Q2 = QuadFE(1,'Q2')
        
        dQ1 = DofHandler(mesh,Q1)
        dQ2 = DofHandler(mesh,Q2)
        
        # Distribute dofs
        [dQ.distribute_dofs() for dQ in [dQ1,dQ2]]
        
        # Basis functions
        phi1 = Basis(dQ1,'u')
        phi2 = Basis(dQ2,'u')
        
        f1 = Nodal(lambda x: x+2, basis=phi1)
        f2 = Nodal(lambda x: x**2 + 1, basis=phi2)
        k = Kernel([f1,f2], F=F)
        
        # Check evaluation
        self.assertTrue(np.allclose(f_t(x), k.eval(x).ravel()))
        
        #
        # Replace f2 above with its derivative
        # 
        k = Kernel([f1,f2], derivatives=['f', 'fx'], F=F)
        f_t = lambda x: (x+2)**2 + 2*x
                
        # Check derivative evaluation F = F(f1, df2_dx)
        self.assertTrue(np.allclose(f_t(x), k.eval(x).ravel()))
        
        
        # 
        # Sampling 
        #
        one = Constant(1)
        f1 = Explicit(lambda x: x**2 + 1, dim=1)
        
        # Sampled function
        a = np.linspace(0,1,11)
        n_samples = len(a)
        
        # Define Dofhandler
        dh = DofHandler(mesh, Q2)
        dh.distribute_dofs()
        dh.set_dof_vertices()
        xv = dh.get_dof_vertices()
        n_dofs = dh.n_dofs()
        
        phi = Basis(dh, 'u')
        
        # Evaluate parameterized function at mesh dof vertices
        f2_m  = np.empty((n_dofs, n_samples))
        for i in range(n_samples):
            f2_m[:,i] = xv.ravel() + a[i]*xv.ravel()**2
        f2 = Nodal(data=f2_m, basis=phi)
        
        # Define kernel
        F = lambda f1, f2, one: f1 + f2 + one
        k = Kernel([f1,f2,one], F=F)
        
        # Evaluate on a fine mesh
        x = np.linspace(0,1,100)
        n_points = len(x)
        self.assertEqual(k.eval(x).shape, (n_points, n_samples))    
        for i in range(n_samples):
            # Check evaluation            
            self.assertTrue(np.allclose(k.eval(x)[:,i], f1.eval(x)[:,i] + x + a[i]*x**2+ 1))
            
        
        #
        # Sample multiple constant functions
        # 
        f1 = Constant(data=a)
        f2 = Explicit(lambda x: 1 + x**2, dim=1)
        f3 = Nodal(data=f2_m[:,-1], basis=phi)
        
        F = lambda f1, f2, f3: f1 + f2 + f3
        k = Kernel([f1,f2,f3], F=F)
        
        x = np.linspace(0,1,100)
        for i in range(n_samples):
            self.assertTrue(np.allclose(k.eval(x)[:,i], \
                                        a[i] + f2.eval(x)[:,i] + f3.eval(x)[:,i]))
        
        #
        # Submeshes
        # 
        mesh = Mesh1D(resolution=(1,))
        mesh_labels = Tree(regular=False)
        
        mesh = Mesh1D(resolution=(1,))
        Q1 = QuadFE(1,'Q1')
        Q2 = QuadFE(1,'Q2')
        
        dQ1 = DofHandler(mesh,Q1)
        dQ2 = DofHandler(mesh,Q2)
        
        # Distribute dofs
        [dQ.distribute_dofs() for dQ in [dQ1,dQ2]]
        
        # Basis
        p1 = Basis(dQ1)
        p2 = Basis(dQ2) 
        
        
        f1 = Nodal(lambda x: x, basis=p1)
        f2 = Nodal(lambda x: -2+2*x**2, basis=p2)
        one = Constant(np.array([1,2]))
    
        F = lambda f1, f2, one: 2*f1**2 + f2 + one
        
        I = mesh.cells.get_child(0)
        
        kernel = Kernel([f1,f2, one], F=F)
        
        rule1D = GaussRule(5,shape='interval')
        x = I.reference_map(rule1D.nodes())
Beispiel #6
0
flag = tuple(mtags.get_node_address())
mesh.cells.record(flag)

mtags.add_child()
new_flag = tuple(mtags.get_child(0).get_node_address())
mesh.cells.refine(subforest_flag=flag, \
                  new_label=new_flag)

for leaf in mesh.cells.get_leaves(subforest_flag=flag):
    leaf.info()

print('==' * 20)

for leaf in mesh.cells.get_leaves(subforest_flag=new_flag):
    leaf.info()

element = QuadFE(1, 'Q2')
dofhandler = DofHandler(mesh, element)
dofhandler.distribute_dofs()
dofhandler.set_dof_vertices()

dofs = dofhandler.get_global_dofs(subforest_flag=flag)
print(dofs)

dofs = dofhandler.get_global_dofs(subforest_flag=new_flag)
print(dofs)

dv = dofhandler.get_dof_vertices(dofs)
print(dv)
Beispiel #7
0
    def test_eval(self):
        #
        # Out of the box covariance kernels
        #
        fig, ax = plt.subplots(6, 4, figsize=(5, 7))

        cov_names = [
            'constant', 'linear', 'gaussian', 'exponential', 'matern',
            'rational'
        ]

        anisotropies = {1: [None, 2], 2: [None, np.diag([2, 1])]}
        m_count = 0
        for mesh in [Mesh1D(resolution=(10, )), QuadMesh(resolution=(10, 10))]:
            # Dimension
            dim = mesh.dim()

            #
            # Construct computational mesh
            #
            # Piecewise constant elements
            element = QuadFE(dim, 'DQ0')

            # Define dofhandler -> get vertices
            dofhandler = DofHandler(mesh, element)
            dofhandler.distribute_dofs()
            dofhandler.set_dof_vertices()
            v = dofhandler.get_dof_vertices()

            # Define meshgrid for 1 and 2 dimensions
            n_dofs = dofhandler.n_dofs()
            M1, M2 = np.mgrid[0:n_dofs, 0:n_dofs]
            if dim == 1:
                X = v[:, 0][M1].ravel()
                Y = v[:, 0][M2].ravel()
            elif dim == 2:
                X = np.array([v[:, 0][M1].ravel(), v[:, 1][M1].ravel()]).T
                Y = np.array([v[:, 0][M2].ravel(), v[:, 1][M2].ravel()]).T

            x = convert_to_array(X, dim=dim)
            y = convert_to_array(Y, dim=dim)
            a_count = 0
            isotropic_label = ['isotropic', 'anisotropic']
            for M in anisotropies[dim]:
                # Cycle through anisotropies

                # Define covariance parameters
                cov_pars = {
                    'constant': {
                        'sgm': 1
                    },
                    'linear': {
                        'sgm': 1,
                        'M': M
                    },
                    'gaussian': {
                        'sgm': 1,
                        'l': 0.1,
                        'M': M
                    },
                    'exponential': {
                        'l': 0.1,
                        'M': M
                    },
                    'matern': {
                        'sgm': 1,
                        'nu': 2,
                        'l': 0.5,
                        'M': M
                    },
                    'rational': {
                        'a': 3,
                        'M': M
                    }
                }

                c_count = 0
                for cov_name in cov_names:

                    C = CovKernel(cov_name, cov_pars[cov_name])
                    Z = C.eval((x, y)).reshape(M1.shape)

                    col = int(m_count * 2**1 + a_count * 2**0)
                    row = c_count
                    ax[row, col].imshow(Z)
                    if col == 0:
                        ax[row, col].set_ylabel(cov_name)

                    if row == 0:
                        ax[row, col].set_title('%dD mesh\n %s' %
                                               (dim, isotropic_label[a_count]))

                    ax[row, col].set_xticks([], [])
                    ax[row, col].set_yticks([], [])

                    c_count += 1
                a_count += 1
            m_count += 1
        fig.savefig('test_covkernel_eval.eps')