Secure your code as it's written. Use Snyk Code to scan source code in minutes - no build needed - and fix issues immediately.
self._extradata = "eqn: "+str(eqn)
if viscosity_mode == 0: # isoviscous
self.fn_eta = fn.misc.constant(1.0)
else: # temp dependent
self.fn_eta = fn.math.exp(-np.log(1000)*tField)
# default value
self.fn_source = 0.
# define function the strain rate 2nd invariant
fn_sr_2ndinv = fn.tensor.second_invariant(fn.tensor.symmetric( vField.fn_gradient ))
if eqn == 'EBA':
# should give these better names
self.viscous_dissipation = 2.0*self.fn_eta*fn_sr_2ndinv
self.adiabatic_heating = -self.Di*fn.math.dot(annulus._fn_unitvec_radial(), vField) * (tField + T_s)
self.fn_source = self.Di / self.Ra * self.viscous_dissipation + self.adiabatic_heating
self.fn_force = tField * Ra * annulus._fn_unitvec_radial()
# setups the systems
self.model_init()
# flag setups as staged
self._staged_setup = 1
# In[14]:
advector = uw.systems.SwarmAdvector( swarm=swarm, velocityField=velocityField, order=2 )
# Analysis tools
# -----
#
# **RMS velocity**
#
# Set up integrals used to calculate the RMS velocity.
# In[15]:
vdotv = fn.math.dot( velocityField, velocityField )
v2sum_integral = uw.utils.Integral( mesh=mesh, fn=vdotv )
volume_integral = uw.utils.Integral( mesh=mesh, fn=1. )
# Main simulation loop
# -----
#
# The main time stepping loop begins here. Before this the time and timestep are initialised to zero and the output statistics arrays are set up. Also the frequency of outputting basic statistics to the screen is set in steps_output.
#
# Note that there are two ``advector.integrate`` steps, one for each swarm, that need to be done each time step.
# In[16]:
# Stepping. Initialise time and timestep.
time = 0.
step = 0
def fn_unitvec_radial(self):
pos = fn.coord()
centre = self._centroid
r_vec = pos - centre
mag = fn.math.sqrt(fn.math.dot( r_vec, r_vec ))
r_vec = r_vec / mag
return r_vec
def _fn_unitvec_theta(self):
pos = fn.coord()
r = fn.math.sqrt(fn.math.dot( pos, pos ))
theta = fn.math.atan2(pos[1],pos[0])
vec = -fn.math.sin(theta) * (1.0, 0.0)
vec += fn.math.cos(theta) * (0.0, 1.0)
return vec
# a mass matrix goes into the lower right block of the stokes system coeff matrix
self._mmatrix = sle.AssembledMatrix( self._pressureSol, self._pressureSol, rhs=self._hvector )
# -1. as per Hughes, The Finite Element Method, 1987, Table 4.3.1, [M]
self._compressibleTerm = sle.MatrixAssemblyTerm_NA__NB__Fn( integrationSwarm=intswarm,
assembledObject=self._mmatrix,
mesh=mesh,
fn=self._fn_minus_one_on_lambda )
if fn_stresshistory != None:
self._NA_j__Fn_ijTerm = sle.VectorAssemblyTerm_NA_j__Fn_ij( integrationSwarm=intswarm,
assembledObject=self._fvector,
fn=fn_stresshistory )
# objects used for analysis, dictionary for organisation
self._aObjects = dict()
self._aObjects['vdotv_fn'] = uw.function.math.dot( self._velocityField, self._velocityField )
super(Stokes, self).__init__(**kwargs)
# $$\langle W \rangle = \int^1_0 \int^1_0 T u_y \, dx dy$$
# * and the average rate of viscous dissipation
# $$\langle \Phi \rangle = \int^1_0 \int^1_0 \tau_{ij} \dot \epsilon_{ij} \, dx dy$$
#
# * In steady state, if thermal energy is accurately conserved, the difference between $\langle W \rangle$ and $\langle \Phi \rangle / Ra$ must vanish, so also reported is the percentage error:
#
# $$ \delta = \frac{\lvert \langle W \rangle - \frac{\langle \Phi \rangle}{Ra} \rvert}{max \left( \langle W \rangle, \frac{\langle \Phi \rangle}{Ra}\right)} \times 100% $$
# **Setup volume integrals used in metric functions**
# In[ ]:
tempint = uw.utils.Integral( temperatureField, mesh )
areaint = uw.utils.Integral( 1., mesh )
v2int = uw.utils.Integral( fn.math.dot(velocityField,velocityField), mesh )
dwint = uw.utils.Integral( temperatureField*velocityField[1], mesh )
sinner = fn.math.dot( secinv, secinv )
vdint = uw.utils.Integral( (4.*viscosityFn*sinner), mesh )
# **Setup surface integrals used in metric functions**
# In[ ]:
rmsSurfInt = uw.utils.Integral( fn=velocityField[0]*velocityField[0], mesh=mesh, integrationType='Surface',
surfaceIndexSet=mesh.specialSets["MaxJ_VertexSet"])
nuTop = uw.utils.Integral( fn=temperatureField.gradientFn[1], mesh=mesh, integrationType='Surface',
surfaceIndexSet=mesh.specialSets["MaxJ_VertexSet"])
nuBottom = uw.utils.Integral( fn=temperatureField.gradientFn[1], mesh=mesh, integrationType='Surface',
def remove_velocity_null_space(self, vField):
# This is a sort-of null space !
vField.data[:,:] *= self.maskFn.evaluate(self)
# Value of the null space
null_space_v = uw.utils.Integral(fn.math.dot( vField, self.unitvec_theta_Fn ) * self.radiusFn * self.maskFn, self).evaluate()[0]
null_space_v /= uw.utils.Integral( (self.radiusFn * self.maskFn)**2, self).evaluate()[0]
print("1: Null Space Velocity: {}".format(null_space_v))
# Clean up the solution
vField.data[:,:] -= null_space_v * (self.unitvec_theta_Fn * self.radiusFn * self.maskFn).evaluate(self)[:,:]
return null_space_v