Ejemplo n.º 1
0
def _abs(self):
    return Abs(self)
Ejemplo n.º 2
0
def transient_adv_2d_R22_FV(mesh_2d, s, init_cond, dt_num, steps):
    # Input
    # mu:     diffusivity, constant
    # order:  element order. 1 = linear elements. 2 = quadratic elements.
    # nx:     number of elements
    
    # Output
    # u:      the solution, dolfin function
    
    
    P1 = FiniteElement("DG", mesh_2d.ufl_cell(), 0)
    TH = MixedElement([P1, P1])
    V = FunctionSpace(mesh_2d, TH)
    V0 = V.sub(0).collapse()
    u = TrialFunction(V)
    w = TestFunction(V)
    #u0 = Function(V0)
    u0 = project(init_cond, V0)
    
    DG_space = FunctionSpace(mesh_2d, 'DG', 0)
    Vec = VectorFunctionSpace(mesh_2d, 'CR', 1)
    
    adv = project(Expression( ('sin(pi*x[0])*cos(pi*x[1])', '-cos(pi*x[0])*sin(pi*x[1])'), degree=1 ), Vec )
    
    n = FacetNormal(mesh_2d)
    
    x_ = interpolate(Expression("x[0]", degree=1), DG_space)
    y_ = interpolate(Expression("x[1]",degree=1), DG_space)
    Delta_h = sqrt(jump(x_)**2 + jump(y_)**2)
    
    u_list = [u0.copy()]

    def boundary_L(x, on_boundary):
        return on_boundary and near(x[0], 0, DOLFIN_EPS)

    def boundary_R(x, on_boundary):
        return on_boundary and near(x[0], 1, DOLFIN_EPS)

    bc = []
    
    dt = Constant(dt_num)
    one = Constant(1.0)
    
    adv_np = ( dot ( adv, n ) + Abs ( dot ( adv, n ) ) ) / 2.0
    adv_nm = ( dot ( adv, n ) - Abs ( dot ( adv, n ) ) ) / 2.0
    #adv_n = dot ( adv, n )
    
    def L(w, u):
        #return Constant(0.5)*dot(jump(w), adv_np('+')*u('+') + adv_nm('+')*u('-') )\
        #     + Constant(0.5)*jump(w)*avg(dot( adv, n ))*jump(u)/Delta_h
        #return dot(w('-'), (dot(adv_n, u('-') - u('+') )))
        return dot(jump(w), adv_np('+')*u('+') - adv_np('-')*u('-') )
    
    delta_u = as_vector([(u[0] - u0), (u[1] - u[0])])
    W = as_matrix([[7.0/24, -1.0/24], [13.0/24, 5.0/24]])
    W_inv = inv(W)
    WU = W*delta_u
    #ww = as_vector( [0.5*(w[0]*s-L(w[0], u[1])), 0.5*(w[1]*s-L(w[1], u0))] )
    LL = as_vector([L(w[0], u[0] - u0), L(w[1], u[1] - u[0])])
    ww = as_vector([0.5, 0.5])
    
    
    F = dot( delta_u/dt, as_vector([w[0], w[1]]) )*dx\
        + (L(w[0], WU[0]) + L(w[1], WU[1]))*dS \
        + 0.5*(L(w[0], u0) + L(w[1], u0))*dS \
        - (0.5*(w[0]*s) + 0.5*(w[1]*s))*dx

    
    a, L = lhs(F), rhs(F)

    u = Function(V)
    
    problem = LinearVariationalProblem(a, L, u, bcs=bc)
    solver = LinearVariationalSolver(problem)
    
    prm = solver.parameters
    
    prm['krylov_solver']['absolute_tolerance'] = 1e-12
    prm['krylov_solver']['relative_tolerance'] = 1e-10
    prm['krylov_solver']['maximum_iterations'] = 1000
    #if iterative_solver:
    prm['linear_solver'] = 'gmres'
    prm['preconditioner'] = 'ilu'
    
    for i in range(steps):
        solver.solve()
        
        u1, u2 = u.split(True)
        u0.assign(u2)
        u_list.append(u0.copy())

    return u_list
def steady_adv_diff_1d_FV(mu, nx, s, left_bc, right_bc):
    # Input
    # mu:     diffusivity, constant
    # nx:     number of elements

    # Output
    # u:      the solution, dolfin function

    # mesh of 10 uniform linear elements
    mesh_1d = IntervalMesh(nx, 0, 1)

    h = 1.0 / nx
    adv = as_vector([1.0])
    eta = Constant(1e5)
    one = Constant(1.0)

    Pe = 1.0 * h / (2 * mu)
    print('Peclet number = ', Pe)

    V = FunctionSpace(mesh_1d, 'DG', 0)
    u = TrialFunction(V)
    w = TestFunction(V)

    n = FacetNormal(mesh_1d)

    x_ = interpolate(Expression("x[0]", degree=1), V)
    Delta_h = sqrt(jump(x_)**2)

    boundary_markers = MeshFunction('size_t', mesh_1d, dim=0)

    class left(SubDomain):
        def inside(self, x, on_boundary):
            return on_boundary and near(x[0], 0.0, DOLFIN_EPS)

    class right(SubDomain):
        def inside(self, x, on_boundary):
            return on_boundary and near(x[0], 1.0, DOLFIN_EPS)

    b_left = left()
    b_right = right()

    boundary_markers.set_all(0)

    b_left.mark(boundary_markers, 2)
    b_right.mark(boundary_markers, 3)

    bc = []

    dS = Measure('dS', domain=mesh_1d, subdomain_data=boundary_markers)
    ds = Measure('ds', domain=mesh_1d, subdomain_data=boundary_markers)
    dx = Measure('dx', domain=mesh_1d, subdomain_data=boundary_markers)

    adv_np = (dot(adv, n) + Abs(dot(adv, n))) / 2.0
    adv_nm = (dot(adv, n) - Abs(dot(adv, n))) / 2.0
    #adv_n = dot ( adv, n )

    F = Constant(mu)*jump(w)*jump(u)/Delta_h*dS - w*s*dx\
        - w*(Constant(left_bc) - u)/(x_ - 0.0)*ds(2) - w*(Constant(right_bc) - u)/(one -x_)*ds(3) \
        + jump(w)*(adv_np('+')*u('+') - adv_np('-')*u('-'))*dS(0)\

    a, L = lhs(F), rhs(F)

    u = Function(V)
    solve(a == L, u, bcs=bc)

    return u, V.dofmap().dofs(), V.tabulate_dof_coordinates().T[
        0]  #vertex_to_dof_map(V)
Ejemplo n.º 4
0
def transient_adv_2d_upwind(mesh_2d, s, init_cond, dt_num, steps, theta_num, add_diff):
    # Input
    # nx:     number of elements
    
    # Output
    # u:      the solution, dolfin function

    V = FunctionSpace(mesh_2d, 'DG', 0)
    Vec = VectorFunctionSpace(mesh_2d, 'CR', 1)
    
    u = TrialFunction(V)
    w = TestFunction(V)
    u0 = project(init_cond, V)
    adv = project(Expression( ('sin(pi*x[0])*cos(pi*x[1])', '-cos(pi*x[0])*sin(pi*x[1])'), degree=1 ), Vec )
    
    n = FacetNormal(mesh_2d)
    
    x_ = interpolate(Expression("x[0]", degree=1), V)
    y_ = interpolate(Expression("x[1]",degree=1), V)
    Delta_h = sqrt(jump(x_)**2 + jump(y_)**2)
    
    u_list = [u0.copy()]

    def boundary_L(x, on_boundary):
        return on_boundary and near(x[0], 0, DOLFIN_EPS)

    def boundary_R(x, on_boundary):
        return on_boundary and near(x[0], 1, DOLFIN_EPS)

    #bc_L = DirichletBC(V, Constant(left_bc), boundary_L)
    #bc_R = DirichletBC(V, Constant(right_bc), boundary_R)

    bc = []
    
    dt = Constant(dt_num)
    one = Constant(1.0)
    
    adv_np = ( dot ( adv, n ) + Abs ( dot ( adv, n ) ) ) / 2.0
    adv_nm = ( dot ( adv, n ) - Abs ( dot ( adv, n ) ) ) / 2.0
    adv_n = dot ( adv, n )
    
    def L(w, u):
        return dot(jump(w), adv_np('+')*u('+') + adv_nm('+')*u('-') )
               #- Constant(add_diff)*0.5*dt*jump(dot(adv, adv))*dot(jump(w, n), jump(u, n))/Delta_h
        #return dot(jump(w), adv_np('+')*u('+') - adv_np('-')*u('-') )
        #return Constant(0.5)*w*div(adv*u) + Constant(0.5)*w*dot(adv, grad(u))
        
        
    delta_u = u - u0
    W = 0.5
    ww = (w*s-L(w, u0))
    
    #F = (w*delta_u/dt + W*L(w, u - u0) - ww)*dx
        
    #a, L = lhs(F), rhs(F)
    
    theta = Constant(theta_num)
    
    a = ( w*u/dt )*dx + theta*L(w, u)*dS
    L = ( w*u0/dt + w*s )*dx - (one-theta)*L(w, u0)*dS

    u = Function(V)
    
    problem = LinearVariationalProblem(a, L, u, bcs=bc)
    solver = LinearVariationalSolver(problem)
    
    prm = solver.parameters
    
    prm['krylov_solver']['absolute_tolerance'] = 1e-12
    prm['krylov_solver']['relative_tolerance'] = 1e-10
    prm['krylov_solver']['maximum_iterations'] = 20
    #if iterative_solver:
    prm['linear_solver'] = 'gmres'
    prm['preconditioner'] = 'ilu'
    
    for i in range(steps):
        solver.solve()
        u0.assign(u)
        u_list.append(u0.copy())

    return u_list