示例#1
0
def soroptions(**kwargs):
	#SOROPTIONS - return Relaxation Solver petsc options
	#
	#   Usage:
	#      options=soroptions;
	
	#retrieve options provided in varargin
	arguments=pairoptions.pairoptions(**kwargs) 
	
	options=[['toolkit','petsc'],['mat_type','aij'],['ksp_type','cg'],['pc_type','sor'],['pc_sor_omega',1.1],['pc_sor_its',2]];

	#now, go through our arguments, and write over default options.
	for i in range(len(arguments.list)):
		arg1=arguments.list[i][0]
		arg2=arguments.list[i][1]
		found=0;
		for j in range(len(options)):
			joption=options[j][0]
			if joption==arg1:
				joption[1]=arg2;
				options[j]=joption;
				found=1;
				break
		if not found:
			#this option did not exist, add it: 
			options.append([arg1,arg2])
	return options
示例#2
0
def jacobicgoptions(*args):
	#ASMOPTIONS - return Additive Shwartz Method with Jacobi preconditioner petsc options
	#
	#   Usage:
	#      options=jacobicgoptions;
	
	#retrieve options provided in varargin
	arguments=pairoptions.pairoptions(**kwargs) 
	
	options=[['toolkit','petsc'],['mat_type','aij'],['ksp_type','cg'],['ksp_max_it',100],['ksp_rtol',1e-15]];

	#now, go through our arguments, and write over default options.
	for i in range(len(arguments.list)):
		arg1=arguments.list[i][0]
		arg2=arguments.list[i][1]
		found=0;
		for j in range(len(options)):
			joption=options[j][0]
			if joption==arg1:
				joption[1]=arg2;
				options[j]=joption;
				found=1;
				break
		if not found:
			#this option did not exist, add it: 
			options.append([arg1,arg2])
	return options
示例#3
0
def issmgslsolver(*args):
    #ISSMSOLVE - return issm solver options
    #
    #   Usage:
    #      options=issmsolver;

    #retrieve options provided in varargin
    arguments = pairoptions.pairoptions(*args)

    options = OrderedDict()
    options['toolkit'] = 'issm'
    options['mat_type'] = 'dense'
    options['vec_type'] = 'seq'
    options['solver_type'] = 'gsl'

    #now, go through our arguments, and write over default options.
    for i in range(len(arguments.list)):
        arg1 = arguments.list[i][0]
        arg2 = arguments.list[i][1]
        found = 0
        for j in range(len(options)):
            joption = options[j][0]
            if joption == arg1:
                joption[1] = arg2
                options[j] = joption
                found = 1
                break
        if not found:
            #this option did not exist, add it:
            options.append([arg1, arg2])
    return options
示例#4
0
文件: asmoptions.py 项目: pf4d/issm
def asmoptions(*args):
    #ASMOPTIONS - return ASM petsc options
    #
    #   Usage:
    #      options=asmoptions;

    #retrieve options provided in varargin
    arguments = pairoptions.pairoptions(**kwargs)

    options = [['toolkit', 'petsc'],
               ['mat_type', 'aij'], ['ksp_type', 'gmres'], ['pc_type', 'asm'],
               ['sub_pc_type', 'lu'], ['pc_asm_overlap',
                                       3], ['ksp_max_it', 100],
               ['ksp_rtol', 1e-30]]

    #now, go through our arguments, and write over default options.
    for i in range(len(arguments.list)):
        arg1 = arguments.list[i][0]
        arg2 = arguments.list[i][1]
        found = 0
        for j in range(len(options)):
            joption = options[j][0]
            if joption == arg1:
                joption[1] = arg2
                options[j] = joption
                found = 1
                break
        if not found:
            #this option did not exist, add it:
            options.append([arg1, arg2])
    return options
示例#5
0
文件: generic.py 项目: pf4d/issm
	def __init__(self,*args):    # {{{

		self.name=''
		self.login=''
		self.np=1
		self.port=0
		self.interactive=1
		self.codepath=IssmConfig('ISSM_PREFIX')[0]+'/bin'
		self.executionpath=issmdir()+'/execution'
		self.valgrind=issmdir()+'/externalpackages/valgrind/install/bin/valgrind'
		self.valgrindlib=issmdir()+'/externalpackages/valgrind/install/lib/libmpidebug.so'
		self.valgrindsup=issmdir()+'/externalpackages/valgrind/issm.supp'

		#use provided options to change fields
		options=pairoptions(*args)

		#get name
		self.name=socket.gethostname()

		#initialize cluster using user settings if provided
		if os.path.exists(self.name+'_settings.py'):
			execfile(self.name+'_settings.py',globals())

		#OK get other fields
		self=options.AssignObjectFields(self)
示例#6
0
文件: pfe.py 项目: pf4d/issm
	def __init__(self,*args):
		# {{{

		self.name           = 'pfe'
		self.login          = ''
		self.numnodes       = 20
		self.cpuspernode    = 8
		self.port           = 1025
		self.queue          = 'long'
		self.time           = 12*60
		self.processor      = 'wes'
		self.codepath       = ''
		self.executionpath  = ''
		self.grouplist      = 's1010'
		self.interactive    = 0
		self.bbftp          = 0
		self.numstreams     = 8
		self.hyperthreading = 0

		#use provided options to change fields
		options=pairoptions(*args)

		#initialize cluster using user settings if provided
		self=pfe_settings(self)
		self.np=self.nprocs()
		#OK get other fields
		self=options.AssignObjectFields(self)
示例#7
0
def matlaboptions(**kwargs):
    #MATLABOPTIONS - return Matlab petsc options
    #
    #   Usage:
    #      options=matlaboptions;

    #retrieve options provided in varargin
    arguments = pairoptions.pairoptions(**kwargs)

    options = [['toolkit', 'petsc'], ['ksp_type', 'matlab']]

    #now, go through our arguments, and write over default options.
    for i in range(len(arguments.list)):
        arg1 = arguments.list[i][0]
        arg2 = arguments.list[i][1]
        found = 0
        for j in range(len(options)):
            joption = options[j][0]
            if joption == arg1:
                joption[1] = arg2
                options[j] = joption
                found = 1
                break
        if not found:
            #this option did not exist, add it:
            options.append([arg1, arg2])
    return options
示例#8
0
    def __init__(self, *args):  # {{{
        self.name = ''
        self.type = ''
        self.fos_reverse_index = float('NaN')
        self.exp = ''
        self.segments = []
        self.index = -1
        self.nods = 0

        #set defaults
        self.setdefaultparameters()

        #use provided options to change fields
        options = pairoptions(*args)

        self.name = options.getfieldvalue('name', '')
        self.type = options.getfieldvalue('type', '')
        self.exp = options.getfieldvalue('exp', '')
        self.segments = options.getfieldvalue('segments', [])
        self.index = options.getfieldvalue('index', -1)
        self.nods = options.getfieldvalue('nods', 0)

        #if name is mass flux:
        if strcmpi(self.name, 'MassFlux'):
            #make sure that we supplied a file and that it exists!
            if not os.path.exists(self.exp):
                raise IOError(
                    "dependent checkconsistency: specified 'exp' file does not exist!"
                )
            #process the file and retrieve segments
            mesh = options.getfieldvalue('mesh')
            self.segments = MeshProfileIntersection(mesh.elements, mesh.x,
                                                    mesh.y, self.exp)[0]
示例#9
0
文件: mumpsoptions.py 项目: pf4d/issm
def mumpsoptions(**kwargs):
	"""
	MUMPSOPTIONS - return MUMPS direct solver  petsc options

	   Usage:
	      options=mumpsoptions;
	"""

	#retrieve options provided in varargin
	options=pairoptions.pairoptions(**kwargs)
	mumps=OrderedDict()

	#default mumps options
	PETSC_VERSION=IssmConfig('_PETSC_MAJOR_')[0]
	if PETSC_VERSION==2.:
		mumps['toolkit']='petsc'
		mumps['mat_type']=options.getfieldvalue('mat_type','aijmumps')
		mumps['ksp_type']=options.getfieldvalue('ksp_type','preonly')
		mumps['pc_type']=options.getfieldvalue('pc_type','lu')
		mumps['mat_mumps_icntl_14']=options.getfieldvalue('mat_mumps_icntl_14',120)
		mumps['pc_factor_shift_positive_definite']=options.getfieldvalue('pc_factor_shift_positive_definite','true')
	if PETSC_VERSION==3.:
		mumps['toolkit']='petsc'
		mumps['mat_type']=options.getfieldvalue('mat_type','mpiaij')
		mumps['ksp_type']=options.getfieldvalue('ksp_type','preonly')
		mumps['pc_type']=options.getfieldvalue('pc_type','lu')
		mumps['pc_factor_mat_solver_package']=options.getfieldvalue('pc_factor_mat_solver_package','mumps')
		mumps['mat_mumps_icntl_14']=options.getfieldvalue('mat_mumps_icntl_14',120)
		mumps['pc_factor_shift_positive_definite']=options.getfieldvalue('pc_factor_shift_positive_definite','true')

	return mumps
示例#10
0
    def __init__(self, *args):  # {{{

        self.name = ''
        self.definitionstring = ''
        self.profilename = ''
        self.segments = float('NaN')

        #set defaults
        self.setdefaultparameters()

        #use provided options to change fields
        options = pairoptions(*args)

        #OK get other fields
        self = options.AssignObjectFields(self)
示例#11
0
	def __init__(self,**kwargs):    # {{{
		self.name                 = ''
		self.type                 = ''
		self.fos_forward_index    = float('NaN')
		self.fov_forward_indices  = numpy.array([])
		self.nods                 = 0

		#set defaults
		self.setdefaultparameters()

		#use provided options to change fields
		options=pairoptions(**kwargs)

		#OK get other fields
		self=options.AssignObjectFields(self)
示例#12
0
文件: verbose.py 项目: pf4d/issm
    def __init__(self, *args):  # {{{
        #BEGINFIELDS
        self.mprocessor = False
        self.module = False
        self.solution = False
        self.solver = False
        self.convergence = False
        self.control = False
        self.qmu = False
        self.autodiff = False
        self.smb = False
        #ENDFIELDS

        if not len(args):
            #Don't do anything
            self.solution = True
            self.qmu = True
            self.control = True
            pass

        elif len(args) == 1:
            binary = args[0]
            if isinstance(binary, (str, unicode)):
                if binary.lower() == 'all':
                    binary = 2**11 - 1  #all ones
                    self.BinaryToVerbose(binary)
                    self.solver = False  #Do not use by default
                else:
                    binary = int(binary, 2)
                    self.BinaryToVerbose(binary)
            elif isinstance(binary, (int, long, float)):
                self.BinaryToVerbose(int(binary))

        else:
            #Use options to initialize object
            self = pairoptions(*args).AssignObjectFields(self)

            #Cast to logicals
            listproperties = vars(self)
            for fieldname, fieldvalue in listproperties.iteritems():
                if isinstance(fieldvalue, bool) or isinstance(
                        fieldvalue, (int, long, float)):
                    setattr(self, fieldname, bool(fieldvalue))
                else:
                    raise TypeError(
                        "verbose supported field values are logicals only (True or False)"
                    )
示例#13
0
    def __init__(self, *args):
        # {{{
        self.name = 'cyclone'
        self.login = ''
        self.np = 2
        self.time = 100
        self.codepath = ''
        self.executionpath = ''
        self.port = ''
        self.interactive = 0

        #use provided options to change fields
        options = pairoptions(*args)

        #initialize cluster using user settings if provided
        self = cyclone_settings(self)
        #OK get other fields
        self = options.AssignObjectFields(self)
示例#14
0
文件: organizer.py 项目: pf4d/issm
    def __init__(self, **kwargs):  # {{{
        self._currentstep = 0
        self.repository = './'
        self.prefix = 'model.'
        self.trunkprefix = ''
        self.steps = []
        self.requestedsteps = [0]

        #process options
        options = pairoptions.pairoptions(**kwargs)

        #Get prefix
        prefix = options.getfieldvalue('prefix', 'model.')
        if not isinstance(prefix, str):
            raise TypeError("prefix is not a string")
        if not m.strcmp(prefix, prefix.strip()) or len(prefix.split()) > 1:
            raise TypeError("prefix should not have any white space")
        self.prefix = prefix

        #Get repository
        repository = options.getfieldvalue('repository', './')
        if not isinstance(repository, str):
            raise TypeError("repository is not a string")
        if not os.path.isdir(repository):
            raise IOError("Directory '%s' not found" % repository)
        self.repository = repository

        #Get steps
        self.requestedsteps = options.getfieldvalue('steps', [0])

        #Get trunk prefix (only if provided by user)
        if options.exist('trunkprefix'):
            trunkprefix = options.getfieldvalue('trunkprefix', '')
            if not isinstance(trunkprefix, str):
                raise TypeError("trunkprefix is not a string")
            if not m.strcmp(trunkprefix, trunkprefix.strip()) or len(
                    trunkprefix.split()) > 1:
                raise TypeError("trunkprefix should not have any white space")
            self.trunkprefix = trunkprefix
示例#15
0
def iluasmoptions(*args):
    """
	ILUASMOPTIONS - 

	   Usage:
	      options=iluasmoptions;
	"""

    #retrieve options provided in varargin
    options = pairoptions.pairoptions(**kwargs)
    iluasm = OrderedDict()

    #default iluasm options
    iluasm['toolkit'] = 'petsc'
    iluasm['mat_type'] = options.getfieldvalue('mat_type', 'aij')
    iluasm['ksp_type'] = options.getfieldvalue('ksp_type', 'gmres')
    iluasm['pc_type'] = options.getfieldvalue('pc_type', 'asm')
    iluasm['sub_pc_type'] = options.getfieldvalue('sub_pc_type', 'ilu')
    iluasm['pc_asm_overlap'] = options.getfieldvalue('pc_asm_overlap', 5)
    iluasm['ksp_max_it'] = options.getfieldvalue('ksp_max_it', 100)
    iluasm['ksp_rtol'] = options.getfieldvalue('ksp_rtol', 1e-15)

    return iluasm
示例#16
0
def stokesoptions(**kwargs):
    #STOKESOPTIONS - return STOKES multi-physics solver petsc options
    #
    #   Usage:
    #      options=stokesoptions;

    #retrieve options provided in varargin
    arguments = pairoptions.pairoptions(**kwargs)

    #default stokes options
    PETSC_VERSION = IssmConfig('_PETSC_MAJOR_')[0]

    if PETSC_VERSION == 2.:
        raise RuntimeError(
            'stokesoptions error message: multi-physics options not supported in Petsc 2'
        )
    if PETSC_VERSION == 3.:
        options=[['toolkit','petsc'],['mat_type','mpiaij'],['ksp_max_it',1000],['ksp_type','gmres'],['pc_type','fieldsplit'],['pc_field_split_type','schur'],\
       ['fieldsplit_0_pc_type','hypre'],['fieldsplit_0_ksp_type','gmres'],['fieldsplit_0_pc_hypre_type','boomerang'],\
       ['fieldsplit_1_pc_type','jacobi'],['fieldsplit_1_ksp_type','preonly'],['issm_option_solver','stokes']]

    #now, go through our arguments, and write over default options.
    for i in range(len(arguments.list)):
        arg1 = arguments.list[i][0]
        arg2 = arguments.list[i][1]
        found = 0
        for j in range(len(options)):
            joption = options[j][0]
            if joption == arg1:
                joption[1] = arg2
                options[j] = joption
                found = 1
                break
        if not found:
            #this option did not exist, add it:
            options.append([arg1, arg2])
    return options
示例#17
0
文件: vilje.py 项目: pf4d/issm
    def __init__(self, *args):
        # {{{
        self.name = 'vilje'
        self.login = ''
        self.numnodes = 2
        self.cpuspernode = 32
        self.procspernodes = 16
        self.mem = 28
        self.queue = 'workq'
        self.time = 2 * 60
        self.codepath = ''
        self.executionpath = ''
        self.interactive = 0
        self.port = []
        self.accountname = ''

        #use provided options to change fields
        options = pairoptions(*args)

        #initialize cluster using user settings if provided
        self = vilje_settings(self)
        #OK get other fields
        self = options.AssignObjectFields(self)
        self.np = self.numnodes * self.procspernodes
示例#18
0
def checkfield(md, *args):
    """
	CHECKFIELD - check field consistency

	   Used to check model consistency.,
	   Requires: 
	   'field' or 'fieldname' option. If 'fieldname' is provided, it will retrieve it from the model md. (md.(fieldname)) 
             If 'field' is provided, it will assume the argument following 'field' is a numeric array.

	   Available options:
	      - NaN: 1 if check that there is no NaN
	      - size: [lines cols], NaN for non checked dimensions
	      - >:  greater than provided value
	      - >=: greater or equal to provided value
	      - <:  smallerthan provided value
	      - <=: smaller or equal to provided value
	      - < vec:  smallerthan provided values on each vertex
	      - timeseries: 1 if check time series consistency (size and time)
	      - values: cell of strings or vector of acceptable values
	      - numel: list of acceptable number of elements
	      - cell: 1 if check that is cell
	      - empty: 1 if check that non empty
	      - message: overloaded error message

	   Usage:
	      md = checkfield(md,fieldname,options);
	"""

    #get options
    options = pairoptions(*args)

    #get field from model
    if options.exist('field'):
        field = options.getfieldvalue('field')
        fieldname = options.getfieldvalue('fieldname', 'no fieldname')
    else:
        fieldname = options.getfieldvalue('fieldname')
        exec("field=md.{}".format(fieldname))

    if isinstance(field, (bool, int, long, float)):
        field = np.array([field])

    #check empty
    if options.exist('empty'):
        if not field:
            md = md.checkmessage(options.getfieldvalue('message',\
             "field '%s' is empty" % fieldname))

    #Check size
    if options.exist('size'):
        fieldsize = options.getfieldvalue('size')
        if len(fieldsize) == 1:
            if np.isnan(fieldsize[0]):
                pass
            elif np.ndim(field) == 1:
                if not np.size(field) == fieldsize[0]:
                    md = md.checkmessage(
                        options.getfieldvalue(
                            'message', "field {} size should be {}".format(
                                fieldname, fieldsize[0])))
            else:
                try:
                    exec("md.{}=field[:,0]".format(fieldname))
                    print(
                        '{} had a bad dimension, we fixed it but you should check it'
                        .format(fieldname))
                except IndexError:
                    md = md.checkmessage(
                        options.getfieldvalue(
                            'message',
                            "field {} should have {} dimension".format(
                                fieldname, len(fieldsize))))
        elif len(fieldsize) == 2:
            if np.isnan(fieldsize[0]):
                if not np.size(field, 1) == fieldsize[1]:
                    md = md.checkmessage(
                        options.getfieldvalue(
                            'message', "field '%s' should have %d columns" %
                            (fieldname, fieldsize[1])))
            elif np.isnan(fieldsize[1]):
                if not np.size(field, 0) == fieldsize[0]:
                    md = md.checkmessage(
                        options.getfieldvalue(
                            'message', "field '%s' should have %d lines" %
                            (fieldname, fieldsize[0])))
            elif fieldsize[1] == 1:
                if (not np.size(field, 0) == fieldsize[0]):
                    md = md.checkmessage(
                        options.getfieldvalue(
                            'message', "field '%s' size should be %d x %d" %
                            (fieldname, fieldsize[0], fieldsize[1])))
            else:
                if (not np.size(field, 0) == fieldsize[0]) or (not np.size(
                        field, 1) == fieldsize[1]):
                    md = md.checkmessage(
                        options.getfieldvalue(
                            'message', "field '%s' size should be %d x %d" %
                            (fieldname, fieldsize[0], fieldsize[1])))

    #Check numel
    if options.exist('numel'):
        fieldnumel = options.getfieldvalue('numel')
        if np.size(field) not in fieldnumel:
            if len(fieldnumel) == 1:
                md = md.checkmessage(options.getfieldvalue('message',\
                 "field '%s' size should be %d" % (fieldname,fieldnumel)))
            elif len(fieldnumel) == 2:
                md = md.checkmessage(options.getfieldvalue('message',\
                 "field '%s' size should be %d or %d" % (fieldname,fieldnumel[0],fieldnumel[1])))
            else:
                md = md.checkmessage(options.getfieldvalue('message',\
                 "field '%s' size should be %s" % (fieldname,fieldnumel)))

    #check NaN
    if options.getfieldvalue('NaN', 0):
        if np.any(np.isnan(field)):
            md = md.checkmessage(options.getfieldvalue('message',\
             "NaN values found in field '%s'" % fieldname))

    #check Inf
    if options.getfieldvalue('Inf', 0):
        if np.any(np.isinf(field)):
            md = md.checkmessage(options.getfieldvalue('message',\
             "Inf values found in field '%s'" % fieldname))

    #check cell
    if options.getfieldvalue('cell', 0):
        if not isinstance(field, (tuple, list, dict)):
            md = md.checkmessage(options.getfieldvalue('message',\
             "field '%s' should be a cell" % fieldname))

    #check values
    if options.exist('values'):
        fieldvalues = options.getfieldvalue('values')
        if False in m.ismember(field, fieldvalues):
            if len(fieldvalues) == 1:
                md = md.checkmessage(options.getfieldvalue('message',\
                 "field '%s' value should be '%s'"  % (fieldname,fieldvalues[0])))
            elif len(fieldvalues) == 2:
                md = md.checkmessage(options.getfieldvalue('message',\
                 "field '%s' values should be '%s' or '%s'"  % (fieldname,fieldvalues[0],fieldvalues[1])))
            else:
                md = md.checkmessage(options.getfieldvalue('message',\
                 "field '%s' should have values in %s" % (fieldname,fieldvalues)))

    #check greater
    if options.exist('>='):
        lowerbound = options.getfieldvalue('>=')
        if np.any(field < lowerbound):
            md = md.checkmessage(options.getfieldvalue('message',\
             "field '%s' should have values above %d" % (fieldname,lowerbound)))
    if options.exist('>'):
        lowerbound = options.getfieldvalue('>')
        if np.any(field <= lowerbound):
            md = md.checkmessage(options.getfieldvalue('message',\
             "field '%s' should have values above %d" % (fieldname,lowerbound)))

    #check smaller
    if options.exist('<='):
        upperbound = options.getfieldvalue('<=')
        if np.any(field > upperbound):
            md = md.checkmessage(options.getfieldvalue('message',\
             "field '%s' should have values below %d" % (fieldname,upperbound)))
    if options.exist('<'):
        upperbound = options.getfieldvalue('<')
        if np.any(field >= upperbound):
            md = md.checkmessage(options.getfieldvalue('message',\
             "field '%s' should have values below %d" % (fieldname,upperbound)))

    #check file
    if options.getfieldvalue('file', 0):
        if not os.path.exists(field):
            md = md.checkmessage("file provided in '%s': '%s' does not exist" %
                                 (fieldname, field))

    #Check row of strings
    if options.exist('stringrow'):
        if not isinstance(field, list):
            md = md.checkmessage(options.getfieldvalue('message',\
              "field '%s' should be a list" %fieldname))

    #Check forcings (size and times)
    if options.getfieldvalue('timeseries', 0):
        if np.size(field, 0) == md.mesh.numberofvertices:
            if np.ndim(field) > 1 and not np.size(field, 1) == 1:
                md = md.checkmessage(options.getfieldvalue('message',\
                 "field '%s' should have only one column as there are md.mesh.numberofvertices lines" % fieldname))
        elif np.size(field, 0) == md.mesh.numberofvertices + 1 or np.size(
                field, 0) == 2:
            if not all(field[-1, :] == np.sort(field[-1, :])):
                md = md.checkmessage(options.getfieldvalue('message',\
                 "field '%s' columns should be sorted chronologically" % fieldname))
            if any(field[-1, 0:-1] == field[-1, 1:]):
                md = md.checkmessage(options.getfieldvalue('message',\
                 "field '%s' columns must not contain duplicate timesteps" % fieldname))
        else:
            md = md.checkmessage(options.getfieldvalue('message',\
             "field '%s' should have md.mesh.numberofvertices or md.mesh.numberofvertices+1 lines" % fieldname))

    #Check single value forcings (size and times)
    if options.getfieldvalue('singletimeseries', 0):
        if np.size(field, 0) == 2:
            if not all(field[-1, :] == np.sort(field[-1, :])):
                md = md.checkmessage(options.getfieldvalue('message',\
                  "field '%s' columns should be sorted chronologically" % fieldname))
            if any(field[-1, 0:-1] == field[-1, 1:]):
                md = md.checkmessage(options.getfieldvalue('message',\
                  "field '%s' columns must not contain duplicate timesteps" % fieldname))
        else:
            md = md.checkmessage(options.getfieldvalue('message',\
            "field '%s' should have 2 lines" % fieldname))

    return md
示例#19
0
文件: plotoptions.py 项目: pf4d/issm
    def buildlist(self, *arg):  #{{{
        #check length of input
        if len(arg) % 2:
            raise TypeError('Invalid parameter/value pair arguments')

        #go through args and build list (like pairoptions)
        rawoptions = pairoptions.pairoptions(*arg)
        numoptions = len(arg) / 2
        rawlist = [
        ]  # cannot be a dict since they do not support duplicate keys

        for i in xrange(numoptions):
            if isinstance(arg[2 * i], (str, unicode)):
                rawlist.append([arg[2 * i], arg[2 * i + 1]])
            else:
                #option is not a string, ignore it
                print "WARNING: option number %d is not a string and will be ignored." % (
                    i + 1)

        #get figure number
        self.figurenumber = rawoptions.getfieldvalue('figure', 1)
        rawoptions.removefield('figure', 0)

        #get number of subplots
        numberofplots = Counter(x for sublist in rawlist for x in sublist
                                if isinstance(x, (str, unicode)))['data']
        self.numberofplots = numberofplots

        #figure out whether alloptions flag is on
        if rawoptions.getfieldvalue('alloptions', 'off') is 'on':
            allflag = 1
        else:
            allflag = 0

        #initialize self.list (will need a list of dict's (or nested dict) for numberofplots>1)
        #self.list=defaultdict(dict)
        for i in xrange(numberofplots):
            self.list[i] = pairoptions.pairoptions()

        #process plot options
        for i in xrange(len(rawlist)):

            #if alloptions flag is on, apply to all plots
            if (allflag and 'data' not in rawlist[i][0]
                    and '#' not in rawlist[i][0]):

                for j in xrange(numberofplots):
                    self.list[j].addfield(rawlist[i][0], rawlist[i][1])

            elif '#' in rawlist[i][0]:

                #get subplots associated
                string = rawlist[i][0].split('#')
                plotnums = string[-1].split(',')
                field = string[0]

                #loop over plotnums
                for k in xrange(len(plotnums)):
                    plotnum = plotnums[k]

                    #Empty
                    if not plotnum:
                        continue

                        # '#all'
                    elif 'all' in plotnum:
                        for j in xrange(numberofplots):
                            self.list[j].addfield(field, rawlist[i][1])

                    # '#i-j'
                    elif '-' in plotnum:
                        nums = plotnum.split('-')
                        if len(nums) != 2: continue
                        if False in [x.isdigit() for x in nums]:
                            raise ValueError(
                                'error: in option i-j both i and j must be integers'
                            )
                        for j in xrange(int(nums[0]) - 1, int(nums[1])):
                            self.list[j].addfield(field, rawlist[i][1])

                    # Deal with #i
                    else:
                        #assign to subplot
                        if int(plotnum) > numberofplots:
                            raise ValueError(
                                'error: %s cannot be assigned %d which exceeds the number of subplots'
                                % (field, plotnum))
                        self.list[int(plotnum) - 1].addfield(
                            field, rawlist[i][1])
            else:

                #go through all subplots and assign key-value pairs
                j = 0
                while j <= numberofplots - 1:
                    if not self.list[j].exist(rawlist[i][0]):
                        self.list[j].addfield(rawlist[i][0], rawlist[i][1])
                        break
                    else:
                        j = j + 1
                if j + 1 > numberofplots:
                    print "WARNING: too many instances of '%s' in options" % rawlist[
                        i][0]
示例#20
0
def project3d(md, *args):
    """
	PROJECT3D - vertically project a vector from 2d mesh

	   vertically project a vector from 2d mesh (split in noncoll and coll areas) into a 3d mesh.
	   This vector can be a node vector of size (md.mesh.numberofvertices2d,N/A) or an 
	   element vector of size (md.mesh.numberofelements2d,N/A). 
	   arguments: 
	      'vector': 2d vector
	      'type': 'element' or 'node'. 
	   options: 
	      'layer' a layer number where vector should keep its values. If not specified, all layers adopt the 
	             value of the 2d vector.
	      'padding': default to 0 (value adopted by other 3d layers not being projected

	   Examples:
	      extruded_vector=project3d(md,'vector',vector2d,'type','node','layer',1,'padding',NaN)
	      extruded_vector=project3d(md,'vector',vector2d,'type','element','padding',0)
	      extruded_vector=project3d(md,'vector',vector2d,'type','node')
	"""

    #some regular checks
    if not md:
        raise TypeError("bad usage")
    if md.mesh.domaintype().lower() != '3d':
        raise TypeError("input model is not 3d")

    #retrieve parameters from options.
    options = pairoptions(*args)
    vector2d = options.getfieldvalue('vector')  #mandatory
    vectype = options.getfieldvalue('type')  #mandatory
    layer = options.getfieldvalue('layer',
                                  0)  #optional (do all layers otherwise)
    paddingvalue = options.getfieldvalue('padding', 0)  #0 by default

    vector1d = False
    if isinstance(vector2d, np.ndarray) and np.ndim(vector2d) == 1:
        vector1d = True
        vector2d = vector2d.reshape(-1, )

    if isinstance(vector2d,
                  (bool, int, long, float)) or np.size(vector2d) == 1:
        projected_vector = vector2d

    elif vectype.lower() == 'node':

        #Initialize 3d vector
        if np.ndim(vector2d) == 1:
            if vector2d.shape[0] == md.mesh.numberofvertices2d:
                projected_vector = (paddingvalue * np.ones(
                    (md.mesh.numberofvertices))).astype(vector2d.dtype)
            elif vector2d.shape[0] == md.mesh.numberofvertices2d + 1:
                projected_vector = (paddingvalue * np.ones(
                    (md.mesh.numberofvertices + 1))).astype(vector2d.dtype)
                projected_vector[-1] = vector2d[-1]
                vector2d = vector2d[:-1]
            else:
                raise TypeError("vector length not supported")
            #Fill in
            if layer == 0:
                for i in xrange(md.mesh.numberoflayers):
                    projected_vector[(i * md.mesh.numberofvertices2d):(
                        (i + 1) * md.mesh.numberofvertices2d)] = vector2d
            else:
                projected_vector[((layer - 1) * md.mesh.numberofvertices2d):(
                    layer * md.mesh.numberofvertices2d)] = vector2d
        else:
            if vector2d.shape[0] == md.mesh.numberofvertices2d:
                projected_vector = (paddingvalue * np.ones(
                    (md.mesh.numberofvertices, np.size(
                        vector2d, axis=1)))).astype(vector2d.dtype)
            elif vector2d.shape[0] == md.mesh.numberofvertices2d + 1:
                projected_vector = (paddingvalue * np.ones(
                    (md.mesh.numberofvertices + 1, np.size(
                        vector2d, axis=1)))).astype(vector2d.dtype)
                projected_vector[-1, :] = vector2d[-1, :]
                vector2d = vector2d[:-1, :]
            else:
                raise TypeError("vector length not supported")
            #Fill in
            if layer == 0:
                for i in xrange(md.mesh.numberoflayers):
                    projected_vector[(i * md.mesh.numberofvertices2d):(
                        (i + 1) * md.mesh.numberofvertices2d), :] = vector2d
            else:
                projected_vector[((layer - 1) * md.mesh.numberofvertices2d):(
                    layer * md.mesh.numberofvertices2d), :] = vector2d

    elif vectype.lower() == 'element':

        #Initialize 3d vector
        if np.ndim(vector2d) == 1:
            if vector2d.shape[0] == md.mesh.numberofelements2d:
                projected_vector = (paddingvalue * np.ones(
                    (md.mesh.numberofelements))).astype(vector2d.dtype)
            elif vector2d.shape[0] == md.mesh.numberofelements2d + 1:
                projected_vector = (paddingvalue * np.ones(
                    (md.mesh.numberofelements + 1))).astype(vector2d.dtype)
                projected_vector[-1] = vector2d[-1]
                vector2d = vector2d[:-1]
            else:
                raise TypeError("vector length not supported")
            #Fill in
            if layer == 0:
                for i in xrange(md.mesh.numberoflayers - 1):
                    projected_vector[(i * md.mesh.numberofelements2d):(
                        (i + 1) * md.mesh.numberofelements2d)] = vector2d
            else:
                projected_vector[((layer - 1) * md.mesh.numberofelements2d):(
                    layer * md.mesh.numberofelements2d)] = vector2d
        else:
            if vector2d.shape[0] == md.mesh.numberofelements2d:
                projected_vector = (paddingvalue * np.ones(
                    (md.mesh.numberofelements, np.size(
                        vector2d, axis=1)))).astype(vector2d.dtype)
            elif vector2d.shape[0] == md.mesh.numberofelements2d + 1:
                projected_vector = (paddingvalue * np.ones(
                    (md.mesh.numberofelements + 1, np.size(
                        vector2d, axis=1)))).astype(vector2d.dtype)
                projected_vector[-1, :] = vector2d[-1, :]
                vector2d = vector2d[:-1, :]
            else:
                raise TypeError("vector length not supported")
            #Fill in
            if layer == 0:
                for i in xrange(md.mesh.numberoflayers - 1):
                    projected_vector[(i * md.mesh.numberofelements2d):(
                        (i + 1) * md.mesh.numberofelements2d), :] = vector2d
            else:
                projected_vector[((layer - 1) * md.mesh.numberofelements2d):(
                    layer * md.mesh.numberofelements2d), :] = vector2d

    else:
        raise TypeError("project3d error message: unknown projection type")

    if vector1d:
        projected_vector = projected_vector.reshape(-1, )

    return projected_vector
示例#21
0
def setflowequation(md, **kwargs):
    """
	SETFLOWEQUATION - associate a solution type to each element

	   This routine works like plotmodel: it works with an even number of inputs
	   'SIA','SSA','HO','L1L2','FS' and 'fill' are the possible options
	   that must be followed by the corresponding exp file or flags list
	   It can either be a domain file (argus type, .exp extension), or an array of element flags. 
	   If user wants every element outside the domain to be 
	   setflowequationd, add '~' to the name of the domain file (ex: '~HO.exp');
	   an empty string '' will be considered as an empty domain
	   a string 'all' will be considered as the entire domain
	   You can specify the type of coupling, 'penalties' or 'tiling', to use with the input 'coupling'

	   Usage:
	      md=setflowequation(md,varargin)

	   Example:
	      md=setflowequation(md,'HO','HO.exp',fill','SIA','coupling','tiling');
	"""

    #some checks on list of arguments
    if not isinstance(md, model) or not len(kwargs):
        raise TypeError("setflowequation error message")

    #process options
    options = pairoptions(**kwargs)
    print(options)
    #	options=deleteduplicates(options,1);

    #Find_out what kind of coupling to use
    coupling_method = options.getfieldvalue('coupling', 'tiling')
    if coupling_method is not 'tiling' or not 'penalties':
        raise TypeError("coupling type can only be: tiling or penalties")

    #recover elements distribution
    SIAflag = FlagElements(md, options.getfieldvalue('SIA', ''))
    SSAflag = FlagElements(md, options.getfieldvalue('SSA', ''))
    HOflag = FlagElements(md, options.getfieldvalue('HO', ''))
    L1L2flag = FlagElements(md, options.getfieldvalue('L1L2', ''))
    FSflag = FlagElements(md, options.getfieldvalue('FS', ''))
    filltype = options.getfieldvalue('fill', 'none')

    #Flag the elements that have not been flagged as filltype
    if filltype is 'SIA':
        SIAflag[numpy.nonzero(
            numpy.logical_not(p.logical_or_n(SSAflag, HOflag)))] = True
    elif filltype is 'SSA':
        SSAflag[numpy.nonzero(
            numpy.logical_not(p.logical_or_n(SIAflag, HOflag, FSflag)))] = True
    elif filltype is 'HO':
        HOflag[numpy.nonzero(
            numpy.logical_not(p.logical_or_n(SIAflag, SSAflag,
                                             FSflag)))] = True

    #check that each element has at least one flag
    if not any(SIAflag + SSAflag + L1L2flag + HOflag + FSflag):
        raise TypeError(
            "elements type not assigned, supported models are 'SIA','SSA','HO' and 'FS'"
        )

    #check that each element has only one flag
    if any(SIAflag + SSAflag + L1L2flag + HOflag + FSflag > 1):
        print(
            "setflowequation warning message: some elements have several types, higher order type is used for them"
        )
        SIAflag[numpy.nonzero(numpy.logical_and(SIAflag, SSAflag))] = False
        SIAflag[numpy.nonzero(numpy.logical_and(SIAflag, HOflag))] = False
        SSAflag[numpy.nonzero(numpy.logical_and(SSAflag, HOflag))] = False

    #FS can only be used alone for now:
    if any(FSflag) and any(SIAflag):
        raise TypeError(
            "FS cannot be used with any other model for now, put FS everywhere"
        )

    #Initialize node fields
    nodeonSIA = numpy.zeros(md.mesh.numberofvertices, bool)
    nodeonSIA[md.mesh.elements[numpy.nonzero(SIAflag), :] - 1] = True
    nodeonSSA = numpy.zeros(md.mesh.numberofvertices, bool)
    nodeonSSA[md.mesh.elements[numpy.nonzero(SSAflag), :] - 1] = True
    nodeonL1L2 = numpy.zeros(md.mesh.numberofvertices, bool)
    nodeonL1L2[md.mesh.elements[numpy.nonzero(L1L2flag), :] - 1] = True
    nodeonHO = numpy.zeros(md.mesh.numberofvertices, bool)
    nodeonHO[md.mesh.elements[numpy.nonzero(HOflag), :] - 1] = True
    nodeonFS = numpy.zeros(md.mesh.numberofvertices, bool)
    noneflag = numpy.zeros(md.mesh.numberofelements, bool)

    #First modify FSflag to get rid of elements contrained everywhere (spc + border with HO or SSA)
    if any(FSflag):
        #		fullspcnodes=double((~isnan(md.stressbalance.spcvx)+~isnan(md.stressbalance.spcvy)+~isnan(md.stressbalance.spcvz))==3 | (nodeonHO & nodeonFS));         %find all the nodes on the boundary of the domain without icefront
        fullspcnodes=numpy.logical_or(numpy.logical_not(numpy.isnan(md.stressbalance.spcvx)).astype(int)+ \
                                      numpy.logical_not(numpy.isnan(md.stressbalance.spcvy)).astype(int)+ \
                                      numpy.logical_not(numpy.isnan(md.stressbalance.spcvz)).astype(int)==3, \
                                      numpy.logical_and(nodeonHO,nodeonFS)).astype(int)    #find all the nodes on the boundary of the domain without icefront
        #		fullspcelems=double(sum(fullspcnodes(md.mesh.elements),2)==6);         %find all the nodes on the boundary of the domain without icefront
        fullspcelems = (
            numpy.sum(fullspcnodes[md.mesh.elements - 1], axis=1) == 6
        ).astype(
            int
        )  #find all the nodes on the boundary of the domain without icefront
        FSflag[numpy.nonzero(fullspcelems.reshape(-1))] = False
        nodeonFS[md.mesh.elements[numpy.nonzero(FSflag), :] - 1] = True

    #Then complete with NoneApproximation or the other model used if there is no FS
    if any(FSflag):
        if any(HOflag):  #fill with HO
            HOflag[numpy.logical_not(FSflag)] = True
            nodeonHO[md.mesh.elements[numpy.nonzero(HOflag), :] - 1] = True
        elif any(SSAflag):  #fill with SSA
            SSAflag[numpy.logical_not(FSflag)] = True
            nodeonSSA[md.mesh.elements[numpy.nonzero(SSAflag), :] - 1] = True
        else:  #fill with none
            noneflag[numpy.nonzero(numpy.logical_not(FSflag))] = True

    #Now take care of the coupling between SSA and HO
    md.stressbalance.vertex_pairing = numpy.array([])
    nodeonSSAHO = numpy.zeros(md.mesh.numberofvertices, bool)
    nodeonHOFS = numpy.zeros(md.mesh.numberofvertices, bool)
    nodeonSSAFS = numpy.zeros(md.mesh.numberofvertices, bool)
    SSAHOflag = numpy.zeros(md.mesh.numberofelements, bool)
    SSAFSflag = numpy.zeros(md.mesh.numberofelements, bool)
    HOFSflag = numpy.zeros(md.mesh.numberofelements, bool)
    if coupling_method is 'penalties':
        #Create the border nodes between HO and SSA and extrude them
        numnodes2d = md.mesh.numberofvertices2d
        numlayers = md.mesh.numberoflayers
        bordernodes2d = numpy.nonzero(
            numpy.logical_and(nodeonHO[0:numnodes2d], nodeonSSA[0:numnodes2d])
        )[0] + 1  #Nodes connected to two different types of elements

        #initialize and fill in penalties structure
        if numpy.all(numpy.logical_not(numpy.isnan(bordernodes2d))):
            penalties = numpy.zeros((0, 2))
            for i in range(1, numlayers):
                penalties = numpy.vstack(
                    (penalties,
                     numpy.hstack((bordernodes2d.reshape(-1, 1),
                                   bordernodes2d.reshape(-1, 1) +
                                   md.mesh.numberofvertices2d * (i)))))
            md.stressbalance.vertex_pairing = penalties

    elif coupling_method is 'tiling':
        if any(SSAflag) and any(HOflag):  #coupling SSA HO
            #Find node at the border
            nodeonSSAHO[numpy.nonzero(numpy.logical_and(nodeonSSA,
                                                        nodeonHO))] = True
            #SSA elements in contact with this layer become SSAHO elements
            matrixelements = m.ismember(md.mesh.elements - 1,
                                        numpy.nonzero(nodeonSSAHO)[0])
            commonelements = numpy.sum(matrixelements, axis=1) != 0
            commonelements[numpy.nonzero(
                HOflag
            )] = False  #only one layer: the elements previously in SSA
            SSAflag[numpy.nonzero(
                commonelements)] = False  #these elements are now SSAHOelements
            SSAHOflag[numpy.nonzero(commonelements)] = True
            nodeonSSA[:] = False
            nodeonSSA[md.mesh.elements[numpy.nonzero(SSAflag), :] - 1] = True

            #rule out elements that don't touch the 2 boundaries
            pos = numpy.nonzero(SSAHOflag)[0]
            elist = numpy.zeros(numpy.size(pos), dtype=int)
            elist = elist + numpy.sum(nodeonSSA[md.mesh.elements[pos, :] - 1],
                                      axis=1).astype(bool)
            elist = elist - numpy.sum(nodeonHO[md.mesh.elements[pos, :] - 1],
                                      axis=1).astype(bool)
            pos1 = numpy.nonzero(elist == 1)[0]
            SSAflag[pos[pos1]] = True
            SSAHOflag[pos[pos1]] = False
            pos2 = numpy.nonzero(elist == -1)[0]
            HOflag[pos[pos2]] = True
            SSAHOflag[pos[pos2]] = False

            #Recompute nodes associated to these elements
            nodeonSSA[:] = False
            nodeonSSA[md.mesh.elements[numpy.nonzero(SSAflag), :] - 1] = True
            nodeonHO[:] = False
            nodeonHO[md.mesh.elements[numpy.nonzero(HOflag), :] - 1] = True
            nodeonSSAHO[:] = False
            nodeonSSAHO[md.mesh.elements[numpy.nonzero(SSAHOflag), :] -
                        1] = True

        elif any(HOflag) and any(FSflag):  #coupling HO FS
            #Find node at the border
            nodeonHOFS[numpy.nonzero(numpy.logical_and(nodeonHO,
                                                       nodeonFS))] = True
            #FS elements in contact with this layer become HOFS elements
            matrixelements = m.ismember(md.mesh.elements - 1,
                                        numpy.nonzero(nodeonHOFS)[0])
            commonelements = numpy.sum(matrixelements, axis=1) != 0
            commonelements[numpy.nonzero(
                HOflag
            )] = False  #only one layer: the elements previously in SSA
            FSflag[numpy.nonzero(
                commonelements)] = False  #these elements are now SSAHOelements
            HOFSflag[numpy.nonzero(commonelements)] = True
            nodeonFS = numpy.zeros(md.mesh.numberofvertices, bool)
            nodeonFS[md.mesh.elements[numpy.nonzero(FSflag), :] - 1] = True

            #rule out elements that don't touch the 2 boundaries
            pos = numpy.nonzero(HOFSflag)[0]
            elist = numpy.zeros(numpy.size(pos), dtype=int)
            elist = elist + numpy.sum(nodeonFS[md.mesh.elements[pos, :] - 1],
                                      axis=1).astype(bool)
            elist = elist - numpy.sum(nodeonHO[md.mesh.elements[pos, :] - 1],
                                      axis=1).astype(bool)
            pos1 = numpy.nonzero(elist == 1)[0]
            FSflag[pos[pos1]] = True
            HOFSflag[pos[pos1]] = False
            pos2 = numpy.nonzero(elist == -1)[0]
            HOflag[pos[pos2]] = True
            HOFSflag[pos[pos2]] = False

            #Recompute nodes associated to these elements
            nodeonFS[:] = False
            nodeonFS[md.mesh.elements[numpy.nonzero(FSflag), :] - 1] = True
            nodeonHO[:] = False
            nodeonHO[md.mesh.elements[numpy.nonzero(HOflag), :] - 1] = True
            nodeonHOFS[:] = False
            nodeonHOFS[md.mesh.elements[numpy.nonzero(HOFSflag), :] - 1] = True

        elif any(FSflag) and any(SSAflag):
            #Find node at the border
            nodeonSSAFS[numpy.nonzero(numpy.logical_and(nodeonSSA,
                                                        nodeonFS))] = True
            #FS elements in contact with this layer become SSAFS elements
            matrixelements = m.ismember(md.mesh.elements - 1,
                                        numpy.nonzero(nodeonSSAFS)[0])
            commonelements = numpy.sum(matrixelements, axis=1) != 0
            commonelements[numpy.nonzero(
                SSAflag
            )] = False  #only one layer: the elements previously in SSA
            FSflag[numpy.nonzero(
                commonelements
            )] = False  #these elements are now SSASSAelements
            SSAFSflag[numpy.nonzero(commonelements)] = True
            nodeonFS = numpy.zeros(md.mesh.numberofvertices, bool)
            nodeonFS[md.mesh.elements[numpy.nonzero(FSflag), :] - 1] = True

            #rule out elements that don't touch the 2 boundaries
            pos = numpy.nonzero(SSAFSflag)[0]
            elist = numpy.zeros(numpy.size(pos), dtype=int)
            elist = elist + numpy.sum(nodeonSSA[md.mesh.elements[pos, :] - 1],
                                      axis=1).astype(bool)
            elist = elist - numpy.sum(nodeonFS[md.mesh.elements[pos, :] - 1],
                                      axis=1).astype(bool)
            pos1 = numpy.nonzero(elist == 1)[0]
            SSAflag[pos[pos1]] = True
            SSAFSflag[pos[pos1]] = False
            pos2 = numpy.nonzero(elist == -1)[0]
            FSflag[pos[pos2]] = True
            SSAFSflag[pos[pos2]] = False

            #Recompute nodes associated to these elements
            nodeonSSA[:] = False
            nodeonSSA[md.mesh.elements[numpy.nonzero(SSAflag), :] - 1] = True
            nodeonFS[:] = False
            nodeonFS[md.mesh.elements[numpy.nonzero(FSflag), :] - 1] = True
            nodeonSSAFS[:] = False
            nodeonSSAFS[md.mesh.elements[numpy.nonzero(SSAFSflag), :] -
                        1] = True

        elif any(FSflag) and any(SIAflag):
            raise TypeError("type of coupling not supported yet")

    #Create SSAHOApproximation where needed
    md.flowequation.element_equation = numpy.zeros(md.mesh.numberofelements,
                                                   int)
    md.flowequation.element_equation[numpy.nonzero(noneflag)] = 0
    md.flowequation.element_equation[numpy.nonzero(SIAflag)] = 1
    md.flowequation.element_equation[numpy.nonzero(SSAflag)] = 2
    md.flowequation.element_equation[numpy.nonzero(L1L2flag)] = 3
    md.flowequation.element_equation[numpy.nonzero(HOflag)] = 4
    md.flowequation.element_equation[numpy.nonzero(FSflag)] = 5
    md.flowequation.element_equation[numpy.nonzero(SSAHOflag)] = 6
    md.flowequation.element_equation[numpy.nonzero(SSAFSflag)] = 7
    md.flowequation.element_equation[numpy.nonzero(HOFSflag)] = 8

    #border
    md.flowequation.borderHO = nodeonHO
    md.flowequation.borderSSA = nodeonSSA
    md.flowequation.borderFS = nodeonFS

    #Create vertices_type
    md.flowequation.vertex_equation = numpy.zeros(md.mesh.numberofvertices,
                                                  int)
    pos = numpy.nonzero(nodeonSSA)
    md.flowequation.vertex_equation[pos] = 2
    pos = numpy.nonzero(nodeonL1L2)
    md.flowequation.vertex_equation[pos] = 3
    pos = numpy.nonzero(nodeonHO)
    md.flowequation.vertex_equation[pos] = 4
    pos = numpy.nonzero(nodeonFS)
    md.flowequation.vertex_equation[pos] = 5
    #DO SIA LAST! Otherwise spcs might not be set up correctly (SIA should have priority)
    pos = numpy.nonzero(nodeonSIA)
    md.flowequation.vertex_equation[pos] = 1
    if any(FSflag):
        pos = numpy.nonzero(numpy.logical_not(nodeonFS))
        if not (any(HOflag) or any(SSAflag)):
            md.flowequation.vertex_equation[pos] = 0
    pos = numpy.nonzero(nodeonSSAHO)
    md.flowequation.vertex_equation[pos] = 6
    pos = numpy.nonzero(nodeonHOFS)
    md.flowequation.vertex_equation[pos] = 7
    pos = numpy.nonzero(nodeonSSAFS)
    md.flowequation.vertex_equation[pos] = 8

    #figure out solution types
    md.flowequation.isSIA = any(md.flowequation.element_equation == 1)
    md.flowequation.isSSA = any(md.flowequation.element_equation == 2)
    md.flowequation.isL1L2 = any(md.flowequation.element_equation == 3)
    md.flowequation.isHO = any(md.flowequation.element_equation == 4)
    md.flowequation.isFS = any(md.flowequation.element_equation == 5)

    return md

    #Check that tiling can work:
    if any(md.flowequation.borderSSA) and any(
            md.flowequation.borderHO) and any(
                md.flowequation.borderHO + md.flowequation.borderSSA != 1):
        raise TypeError("error coupling domain too irregular")
    if any(md.flowequation.borderSSA) and any(
            md.flowequation.borderFS) and any(
                md.flowequation.borderFS + md.flowequation.borderSSA != 1):
        raise TypeError("error coupling domain too irregular")
    if any(md.flowequation.borderFS) and any(md.flowequation.borderHO) and any(
            md.flowequation.borderHO + md.flowequation.borderFS != 1):
        raise TypeError("error coupling domain too irregular")

    return md
示例#22
0
文件: bamg.py 项目: pf4d/issm
def bamg(md, *kwargs):
    """
	BAMG - mesh generation

	   Available options (for more details see ISSM website http://issm.jpl.nasa.gov/):

	   - domain :            followed by an ARGUS file that prescribes the domain outline
	   - hmin :              minimum edge length (default is 10^-100)
	   - hmax :              maximum edge length (default is 10^100)
	   - hVertices :         imposed edge length for each vertex (geometry or mesh)
	   - hminVertices :      minimum edge length for each vertex (mesh)
	   - hmaxVertices :      maximum edge length for each vertex (mesh)

	   - anisomax :          maximum ratio between the smallest and largest edges (default is 10^30)
	   - coeff :             coefficient applied to the metric (2-> twice as many elements, default is 1)
	   - cutoff :            scalar used to compute the metric when metric type 2 or 3 are applied
	   - err :               error used to generate the metric from a field
	   - errg :              geometric error (default is 0.1)
	   - field :             field of the model that will be used to compute the metric
	                         to apply several fields, use one column per field
	   - gradation :         maximum ratio between two adjacent edges
	   - Hessiantype :       0 -> use double P2 projection (default)
	                         1 -> use Green formula
	   - KeepVertices :      try to keep initial vertices when adaptation is done on an existing mesh (default 1)
	   - MaxCornerAngle :    maximum angle of corners in degree (default is 10)
	   - maxnbv :            maximum number of vertices used to allocate memory (default is 10^6)
	   - maxsubdiv :         maximum subdivision of exisiting elements (default is 10)
	   - metric :            matrix (numberofnodes x 3) used as a metric
	   - Metrictype :        1 -> absolute error          c/(err coeff^2) * Abs(H)        (default)
	                         2 -> relative error          c/(err coeff^2) * Abs(H)/max(s,cutoff*max(s))
	                         3 -> rescaled absolute error c/(err coeff^2) * Abs(H)/(smax-smin)
	   - nbjacoby :          correction used by Hessiantype=1 (default is 1)
	   - nbsmooth :          number of metric smoothing procedure (default is 3)
	   - omega :             relaxation parameter of the smoothing procedure (default is 1.8)
	   - power :             power applied to the metric (default is 1)
	   - splitcorners :      split triangles whuch have 3 vertices on the outline (default is 1)
	   - geometricalmetric : take the geometry into account to generate the metric (default is 0)
	   - verbose :           level of verbosity (default is 1)

	   - rifts :             followed by an ARGUS file that prescribes the rifts
	   - toltip :            tolerance to move tip on an existing point of the domain outline
	   - tracks :            followed by an ARGUS file that prescribes the tracks that the mesh will stick to
	   - RequiredVertices :  mesh vertices that are required. [x,y,ref]; ref is optional
	   - tol :               if the distance between 2 points of the domain outline is less than tol, they
	                         will be merged

	   Examples:
	      md=bamg(md,'domain','DomainOutline.exp','hmax',3000);
	      md=bamg(md,'field',[md.inversion.vel_obs md.geometry.thickness],'hmax',20000,'hmin',1000);
	      md=bamg(md,'metric',A,'hmin',1000,'hmax',20000,'gradation',3,'anisomax',1);
	"""

    #process options
    options = pairoptions(**kwargs)
    #	options=deleteduplicates(options,1);

    #initialize the structures required as input of Bamg
    bamg_options = OrderedDict()
    bamg_geometry = bamggeom()
    bamg_mesh = bamgmesh()

    # Bamg Geometry parameters {{{
    if options.exist('domain'):

        #Check that file exists
        domainfile = options.getfieldvalue('domain')
        if not os.path.exists(domainfile):
            raise IOError("bamg error message: file '%s' not found" %
                          domainfile)
        domain = expread(domainfile)

        #Build geometry
        count = 0
        for i, domaini in enumerate(domain):

            #Check that the domain is closed
            if (domaini['x'][0] != domaini['x'][-1]
                    or domaini['y'][0] != domaini['y'][-1]):
                raise RuntimeError(
                    "bamg error message: all contours provided in ''domain'' should be closed"
                )

            #Checks that all holes are INSIDE the principle domain outline
            if i:
                flags = ContourToNodes(domaini['x'], domaini['y'], domainfile,
                                       0)
                if numpy.any(numpy.logical_not(flags)):
                    raise RuntimeError(
                        "bamg error message: All holes should be strictly inside the principal domain"
                    )

            #Add all points to bamg_geometry
            nods = domaini['nods'] - 1  #the domain are closed 0=end
            bamg_geometry.Vertices = numpy.vstack(
                (bamg_geometry.Vertices,
                 numpy.hstack(
                     (domaini['x'][0:nods].reshape(-1, 1),
                      domaini['y'][0:nods].reshape(-1, 1), numpy.ones(
                          (nods, 1))))))
            bamg_geometry.Edges = numpy.vstack(
                (bamg_geometry.Edges,
                 numpy.hstack(
                     (numpy.arange(count + 1, count + nods + 1).reshape(-1, 1),
                      numpy.hstack((numpy.arange(count + 2, count + nods + 1),
                                    count + 1)).reshape(-1,
                                                        1), 1. * numpy.ones(
                                                            (nods, 1))))))
            if i:
                bamg_geometry.SubDomains = numpy.vstack(
                    (bamg_geometry.SubDomains, [2, count + 1, 1, 1]))

            #update counter
            count += nods

        #take care of rifts
        if options.exist('rifts'):

            #Check that file exists
            riftfile = options.getfieldvalue('rifts')
            if not os.path.exists(riftfile):
                raise IOError("bamg error message: file '%s' not found" %
                              riftfile)
            rift = expread(riftfile)

            for i, rifti in enumerate(rift):

                #detect whether all points of the rift are inside the domain
                flags = ContourToNodes(rifti['x'], rifti['y'], domain[0], 0)
                if numpy.all(numpy.logical_not(flags)):
                    raise RuntimeError(
                        "one rift has all its points outside of the domain outline"
                    )

                elif numpy.any(numpy.logical_not(flags)):
                    #We LOTS of work to do
                    print(
                        "Rift tip outside of or on the domain has been detected and is being processed..."
                    )

                    #check that only one point is outside (for now)
                    if numpy.sum(numpy.logical_not(flags).astype(int)) != 1:
                        raise RuntimeError(
                            "bamg error message: only one point outside of the domain is supported yet"
                        )

                    #Move tip outside to the first position
                    if not flags[0]:
                        #OK, first point is outside (do nothing),
                        pass
                    elif not flags[-1]:
                        rifti['x'] = numpy.flipud(rifti['x'])
                        rifti['y'] = numpy.flipud(rifti['y'])
                    else:
                        raise RuntimeError(
                            "bamg error message: only a rift tip can be outside of the domain"
                        )

                    #Get cordinate of intersection point
                    x1 = rifti['x'][0]
                    y1 = rifti['y'][0]
                    x2 = rifti['x'][1]
                    y2 = rifti['y'][1]
                    for j in range(0, numpy.size(domain[0]['x']) - 1):
                        if SegIntersect(
                                numpy.array([[x1, y1], [x2, y2]]),
                                numpy.array(
                                    [[domain[0]['x'][j], domain[0]['y'][j]],
                                     [
                                         domain[0]['x'][j + 1],
                                         domain[0]['y'][j + 1]
                                     ]])):

                            #Get position of the two nodes of the edge in domain
                            i1 = j
                            i2 = j + 1

                            #rift is crossing edge [i1 i2] of the domain
                            #Get coordinate of intersection point (http://mathworld.wolfram.com/Line-LineIntersection.html)
                            x3 = domain[0]['x'][i1]
                            y3 = domain[0]['y'][i1]
                            x4 = domain[0]['x'][i2]
                            y4 = domain[0]['y'][i2]
                            #							x=det([det([x1 y1; x2 y2])  x1-x2;det([x3 y3; x4 y4])  x3-x4])/det([x1-x2 y1-y2;x3-x4 y3-y4]);
                            #							y=det([det([x1 y1; x2 y2])  y1-y2;det([x3 y3; x4 y4])  y3-y4])/det([x1-x2 y1-y2;x3-x4 y3-y4]);
                            x = numpy.linalg.det(
                                numpy.array([[
                                    numpy.linalg.det(
                                        numpy.array([[x1, y1], [x2, y2]])),
                                    x1 - x2
                                ],
                                             [
                                                 numpy.linalg.det(
                                                     numpy.array([[x3, y3],
                                                                  [x4, y4]])),
                                                 x3 - x4
                                             ]])) / numpy.linalg.det(
                                                 numpy.array([[
                                                     x1 - x2, y1 - y2
                                                 ], [x3 - x4, y3 - y4]]))
                            y = numpy.linalg.det(
                                numpy.array([[
                                    numpy.linalg.det(
                                        numpy.array([[x1, y1], [x2, y2]])),
                                    y1 - y2
                                ],
                                             [
                                                 numpy.linalg.det(
                                                     numpy.array([[x3, y3],
                                                                  [x4, y4]])),
                                                 y3 - y4
                                             ]])) / numpy.linalg.det(
                                                 numpy.array([[
                                                     x1 - x2, y1 - y2
                                                 ], [x3 - x4, y3 - y4]]))

                            segdis = sqrt((x4 - x3)**2 + (y4 - y3)**2)
                            tipdis = numpy.array([
                                sqrt((x - x3)**2 + (y - y3)**2),
                                sqrt((x - x4)**2 + (y - y4)**2)
                            ])

                            if numpy.min(
                                    tipdis) / segdis < options.getfieldvalue(
                                        'toltip', 0):
                                print("moving tip-domain intersection point")

                                #Get position of the closer point
                                if tipdis[0] > tipdis[1]:
                                    pos = i2
                                else:
                                    pos = i1

                                #This point is only in Vertices (number pos).
                                #OK, now we can add our own rift
                                nods = rifti['nods'] - 1
                                bamg_geometry.Vertices = numpy.vstack(
                                    (bamg_geometry.Vertices,
                                     numpy.hstack(
                                         (rifti['x'][1:].reshape(-1, 1),
                                          rifti['y'][1:].reshape(-1, 1),
                                          numpy.ones((nods, 1))))))
                                bamg_geometry.Edges=numpy.vstack((bamg_geometry.Edges,\
                                 numpy.array([[pos,count+1,(1+i)]]),\
                                 numpy.hstack((numpy.arange(count+1,count+nods).reshape(-1,1),numpy.arange(count+2,count+nods+1).reshape(-1,1),(1+i)*numpy.ones((nods-1,1))))))
                                count += nods

                                break

                            else:
                                #Add intersection point to Vertices
                                bamg_geometry.Vertices = numpy.vstack(
                                    (bamg_geometry.Vertices,
                                     numpy.array([[x, y, 1]])))
                                count += 1

                                #Decompose the crossing edge into 2 subedges
                                pos = numpy.nonzero(
                                    numpy.logical_and(
                                        bamg_geometry.Edges[:, 0] == i1,
                                        bamg_geometry.Edges[:, 1] == i2))[0]
                                if not pos:
                                    raise RuntimeError(
                                        "bamg error message: a problem occurred..."
                                    )
                                bamg_geometry.Edges=numpy.vstack((bamg_geometry.Edges[0:pos-1,:],\
                                 numpy.array([[bamg_geometry.Edges[pos,0],count                     ,bamg_geometry.Edges[pos,2]]]),\
                                 numpy.array([[count                     ,bamg_geometry.Edges[pos,1],bamg_geometry.Edges[pos,2]]]),\
                                 bamg_geometry.Edges[pos+1:,:]))

                                #OK, now we can add our own rift
                                nods = rifti['nods'] - 1
                                bamg_geometry.Vertices = numpy.vstack(
                                    (bamg_geometry.Vertices,
                                     numpy.hstack(
                                         (rifti['x'][1:].reshape(-1, 1),
                                          rifti['y'][1:].reshape(-1, 1),
                                          numpy.ones((nods, 1))))))
                                bamg_geometry.Edges=numpy.vstack((bamg_geometry.Edges,\
                                 numpy.array([[count,count+1,2]]),\
                                 numpy.hstack((numpy.arange(count+1,count+nods).reshape(-1,1),numpy.arange(count+2,count+nods+1).reshape(-1,1),(1+i)*numpy.ones((nods-1,1))))))
                                count += nods

                                break

                else:
                    nods = rifti['nods'] - 1
                    bamg_geometry.Vertices = numpy.vstack(
                        bamg_geometry.Vertices,
                        numpy.hstack(rifti['x'][:], rifti['y'][:],
                                     numpy.ones((nods + 1, 1))))
                    bamg_geometry.Edges = numpy.vstack(
                        bamg_geometry.Edges,
                        numpy.hstack(
                            numpy.arange(count + 1,
                                         count + nods).reshape(-1, 1),
                            numpy.arange(count + 2,
                                         count + nods + 1).reshape(-1, 1),
                            i * numpy.ones((nods, 1))))
                    count = +nods + 1

        #Deal with tracks
        if options.exist('tracks'):

            #read tracks
            track = options.getfieldvalue('tracks')
            if all(isinstance(track, str)):
                A = expread(track)
                track = numpy.hstack((A.x.reshape(-1, 1), A.y.reshape(-1, 1)))
            else:
                track = float(track)  #for some reason, it is of class "single"
            if numpy.size(track, axis=1) == 2:
                track = numpy.hstack((track, 3. * numpy.ones(
                    (size(track, axis=0), 1))))

            #only keep those inside
            flags = ContourToNodes(track[:, 0], track[:, 1], domainfile, 0)
            track = track[numpy.nonzero(flags), :]

            #Add all points to bamg_geometry
            nods = numpy.size(track, axis=0)
            bamg_geometry.Vertices = numpy.vstack(
                (bamg_geometry.Vertices, track))
            bamg_geometry.Edges = numpy.vstack(
                (bamg_geometry.Edges,
                 numpy.hstack(
                     (numpy.arange(count + 1, count + nods).reshape(-1, 1),
                      numpy.arange(count + 2, count + nods + 1).reshape(-1, 1),
                      3. * numpy.ones((nods - 1, 1))))))

            #update counter
            count += nods

        #Deal with vertices that need to be kept by mesher
        if options.exist('RequiredVertices'):

            #recover RequiredVertices
            requiredvertices = options.getfieldvalue(
                'RequiredVertices')  #for some reason, it is of class "single"
            if numpy.size(requiredvertices, axis=1) == 2:
                requiredvertices = numpy.hstack(
                    (requiredvertices, 4. * numpy.ones(
                        (numpy.size(requiredvertices, axis=0), 1))))

            #only keep those inside
            flags = ContourToNodes(requiredvertices[:, 0],
                                   requiredvertices[:, 1], domainfile, 0)[0]
            requiredvertices = requiredvertices[numpy.nonzero(flags)[0], :]

            #Add all points to bamg_geometry
            nods = numpy.size(requiredvertices, axis=0)
            bamg_geometry.Vertices = numpy.vstack(
                (bamg_geometry.Vertices, requiredvertices))

            #update counter
            count += nods

        #process geom
        #bamg_geometry=processgeometry(bamg_geometry,options.getfieldvalue('tol',float(nan)),domain[0])

    elif isinstance(md.private.bamg, dict) and 'geometry' in md.private.bamg:
        bamg_geometry = bamggeom(md.private.bamg['geometry'].__dict__)
    else:
        #do nothing...
        pass
    #}}}
    # Bamg Mesh parameters {{{
    if not options.exist('domain') and md.mesh.numberofvertices and m.strcmp(
            md.mesh.elementtype(), 'Tria'):

        if isinstance(md.private.bamg, dict) and 'mesh' in md.private.bamg:
            bamg_mesh = bamgmesh(md.private.bamg['mesh'].__dict__)
        else:
            bamg_mesh.Vertices = numpy.hstack(
                (md.mesh.x.reshape(-1, 1), md.mesh.y.reshape(-1, 1),
                 numpy.ones((md.mesh.numberofvertices, 1))))
            bamg_mesh.Triangles = numpy.hstack(
                (md.mesh.elements, numpy.ones((md.mesh.numberofelements, 1))))

        if isinstance(md.rifts.riftstruct, dict):
            raise TypeError(
                "bamg error message: rifts not supported yet. Do meshprocessrift AFTER bamg"
            )
    #}}}
    # Bamg Options {{{
    bamg_options['Crack'] = options.getfieldvalue('Crack', 0)
    bamg_options['anisomax'] = options.getfieldvalue('anisomax', 10.**30)
    bamg_options['coeff'] = options.getfieldvalue('coeff', 1.)
    bamg_options['cutoff'] = options.getfieldvalue('cutoff', 10.**-5)
    bamg_options['err'] = options.getfieldvalue('err', numpy.array([[0.01]]))
    bamg_options['errg'] = options.getfieldvalue('errg', 0.1)
    bamg_options['field'] = options.getfieldvalue('field', numpy.empty((0, 1)))
    bamg_options['gradation'] = options.getfieldvalue('gradation', 1.5)
    bamg_options['Hessiantype'] = options.getfieldvalue('Hessiantype', 0)
    bamg_options['hmin'] = options.getfieldvalue('hmin', 10.**-100)
    bamg_options['hmax'] = options.getfieldvalue('hmax', 10.**100)
    bamg_options['hminVertices'] = options.getfieldvalue(
        'hminVertices', numpy.empty((0, 1)))
    bamg_options['hmaxVertices'] = options.getfieldvalue(
        'hmaxVertices', numpy.empty((0, 1)))
    bamg_options['hVertices'] = options.getfieldvalue('hVertices',
                                                      numpy.empty((0, 1)))
    bamg_options['KeepVertices'] = options.getfieldvalue('KeepVertices', 1)
    bamg_options['MaxCornerAngle'] = options.getfieldvalue(
        'MaxCornerAngle', 10.)
    bamg_options['maxnbv'] = options.getfieldvalue('maxnbv', 10**6)
    bamg_options['maxsubdiv'] = options.getfieldvalue('maxsubdiv', 10.)
    bamg_options['metric'] = options.getfieldvalue('metric', numpy.empty(
        (0, 1)))
    bamg_options['Metrictype'] = options.getfieldvalue('Metrictype', 0)
    bamg_options['nbjacobi'] = options.getfieldvalue('nbjacobi', 1)
    bamg_options['nbsmooth'] = options.getfieldvalue('nbsmooth', 3)
    bamg_options['omega'] = options.getfieldvalue('omega', 1.8)
    bamg_options['power'] = options.getfieldvalue('power', 1.)
    bamg_options['splitcorners'] = options.getfieldvalue('splitcorners', 1)
    bamg_options['geometricalmetric'] = options.getfieldvalue(
        'geometricalmetric', 0)
    bamg_options['random'] = options.getfieldvalue('rand', True)
    bamg_options['verbose'] = options.getfieldvalue('verbose', 1)
    #}}}

    #call Bamg
    [bamgmesh_out,
     bamggeom_out] = BamgMesher(bamg_mesh.__dict__, bamg_geometry.__dict__,
                                bamg_options)

    # plug results onto model
    md.private.bamg = OrderedDict()
    md.private.bamg['mesh'] = bamgmesh(bamgmesh_out)
    md.private.bamg['geometry'] = bamggeom(bamggeom_out)
    md.mesh = mesh2d()
    md.mesh.x = bamgmesh_out['Vertices'][:, 0].copy()
    md.mesh.y = bamgmesh_out['Vertices'][:, 1].copy()
    md.mesh.elements = bamgmesh_out['Triangles'][:, 0:3].astype(int)
    md.mesh.edges = bamgmesh_out['IssmEdges'].astype(int)
    md.mesh.segments = bamgmesh_out['IssmSegments'][:, 0:3].astype(int)
    md.mesh.segmentmarkers = bamgmesh_out['IssmSegments'][:, 3].astype(int)

    #Fill in rest of fields:
    md.mesh.numberofelements = numpy.size(md.mesh.elements, axis=0)
    md.mesh.numberofvertices = numpy.size(md.mesh.x)
    md.mesh.numberofedges = numpy.size(md.mesh.edges, axis=0)
    md.mesh.vertexonboundary = numpy.zeros(md.mesh.numberofvertices, bool)
    md.mesh.vertexonboundary[md.mesh.segments[:, 0:2] - 1] = True
    md.mesh.elementconnectivity = md.private.bamg['mesh'].ElementConnectivity
    md.mesh.elementconnectivity[numpy.nonzero(
        numpy.isnan(md.mesh.elementconnectivity))] = 0
    md.mesh.elementconnectivity = md.mesh.elementconnectivity.astype(int)

    #Check for orphan
    if numpy.any(
            numpy.logical_not(
                numpy.in1d(numpy.arange(1, md.mesh.numberofvertices + 1),
                           md.mesh.elements.flat))):
        raise RuntimeError(
            "Output mesh has orphans. Decrease MaxCornerAngle to prevent outside points (ex: 0.01)"
        )

    return md
示例#23
0
文件: WriteData.py 项目: pf4d/issm
def WriteData(fid, **kwargs):
    """
	WRITEDATA - write model field in binary file
 
	   Usage:
	      WriteData(fid,varargin)
	"""

    #process options
    options = pairoptions.pairoptions(**kwargs)

    #Get data properties
    if options.exist('object'):
        #This is an object field, construct enum and data
        obj = options.getfieldvalue('object')
        fieldname = options.getfieldvalue('fieldname')
        classname = options.getfieldvalue(
            'class',
            str(type(obj)).rsplit('.')[-1].split("'")[0])
        if options.exist('enum'):
            enum = options.getfieldvalue('enum')
        else:
            enum = BuildEnum(classname + '_' + fieldname)
        data = getattr(obj, fieldname)
    else:
        #No processing required
        data = options.getfieldvalue('data')
        enum = options.getfieldvalue('enum')
    format = options.getfieldvalue('format')
    mattype = options.getfieldvalue('mattype', 0)  #only required for matrices
    timeserieslength = options.getfieldvalue('timeserieslength', -1)

    #Process sparse matrices
    #	if issparse(data),
    #		data=full(data);
    #	end

    #Scale data if necesarry
    if options.exist('scale'):
        scale = options.getfieldvalue('scale')
        if numpy.size(data) > 1:
            if numpy.size(data, 0) == timeserieslength:
                data = numpy.array(data)
                data[0:-1, :] = scale * data[0:-1, :]
            else:
                data = scale * data
        else:
            data = scale * data
    if numpy.size(data) > 1:
        if numpy.size(data, 0) == timeserieslength:
            yts = 365.0 * 24.0 * 3600.0
            data[-1, :] = yts * data[-1, :]

    #Step 1: write the enum to identify this record uniquely
    fid.write(struct.pack('i', enum))

    #Step 2: write the data itself.
    if m.strcmpi(format, 'Boolean'):  # {{{
        #		if len(data) !=1:
        #			raise ValueError('field %s cannot be marshalled as it has more than one element!' % EnumToString(enum)[0])

        #first write length of record
        fid.write(struct.pack('i', 4 + 4))  #1 bool (disguised as an int)+code

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write integer
        fid.write(struct.pack(
            'i', int(data)))  #send an int, not easy to send a bool
        # }}}

    elif m.strcmpi(format, 'Integer'):  # {{{
        #		if len(data) !=1:
        #			raise ValueError('field %s cannot be marshalled as it has more than one element!' % EnumToString(enum)[0])

        #first write length of record
        fid.write(struct.pack('i', 4 + 4))  #1 integer + code

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write integer
        fid.write(struct.pack('i', data))
        # }}}

    elif m.strcmpi(format, 'Double'):  # {{{
        #		if len(data) !=1:
        #			raise ValueError('field %s cannot be marshalled as it has more than one element!' % EnumToString(enum)[0])

        #first write length of record
        fid.write(struct.pack('i', 8 + 4))  #1 double+code

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write double
        fid.write(struct.pack('d', data))
        # }}}

    elif m.strcmpi(format, 'String'):  # {{{
        #first write length of record
        fid.write(struct.pack('i',
                              len(data) + 4 + 4))  #string + string size + code

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write string
        fid.write(struct.pack('i', len(data)))
        fid.write(struct.pack('%ds' % len(data), data))
        # }}}

    elif m.strcmpi(format, 'BooleanMat'):  # {{{

        if isinstance(data, bool):
            data = numpy.array([data])
        elif isinstance(data, (list, tuple)):
            data = numpy.array(data).reshape(-1, 1)
        if numpy.ndim(data) == 1:
            if numpy.size(data):
                data = data.reshape(numpy.size(data), 1)
            else:
                data = data.reshape(0, 0)

        #Get size
        s = data.shape
        #if matrix = NaN, then do not write anything
        if s[0] == 1 and s[1] == 1 and math.isnan(data[0][0]):
            s = (0, 0)

        #first write length of record
        fid.write(struct.pack(
            'i', 4 + 4 + 8 * s[0] * s[1] + 4 +
            4))  #2 integers (32 bits) + the double matrix + code + matrix type

        #write data code and matrix type:
        fid.write(struct.pack('i', FormatToCode(format)))
        fid.write(struct.pack('i', mattype))

        #now write matrix
        fid.write(struct.pack('i', s[0]))
        fid.write(struct.pack('i', s[1]))
        for i in range(s[0]):
            for j in range(s[1]):
                fid.write(struct.pack('d', float(
                    data[i]
                    [j])))  #get to the "c" convention, hence the transpose
        # }}}

    elif m.strcmpi(format, 'IntMat'):  # {{{

        if isinstance(data, int):
            data = numpy.array([data])
        elif isinstance(data, (list, tuple)):
            data = numpy.array(data).reshape(-1, 1)
        if numpy.ndim(data) == 1:
            if numpy.size(data):
                data = data.reshape(numpy.size(data), 1)
            else:
                data = data.reshape(0, 0)

        #Get size
        s = data.shape
        #if matrix = NaN, then do not write anything
        if s[0] == 1 and s[1] == 1 and math.isnan(data[0][0]):
            s = (0, 0)

        #first write length of record
        fid.write(struct.pack(
            'i', 4 + 4 + 8 * s[0] * s[1] + 4 +
            4))  #2 integers (32 bits) + the double matrix + code + matrix type

        #write data code and matrix type:
        fid.write(struct.pack('i', FormatToCode(format)))
        fid.write(struct.pack('i', mattype))

        #now write matrix
        fid.write(struct.pack('i', s[0]))
        fid.write(struct.pack('i', s[1]))
        for i in range(s[0]):
            for j in range(s[1]):
                fid.write(struct.pack('d', float(
                    data[i]
                    [j])))  #get to the "c" convention, hence the transpose
        # }}}

    elif m.strcmpi(format, 'DoubleMat'):  # {{{

        if isinstance(data, (bool, int, float)):
            data = numpy.array([data])
        elif isinstance(data, (list, tuple)):
            data = numpy.array(data).reshape(-1, 1)
        if numpy.ndim(data) == 1:
            if numpy.size(data):
                data = data.reshape(numpy.size(data), 1)
            else:
                data = data.reshape(0, 0)

        #Get size
        s = data.shape
        #if matrix = NaN, then do not write anything
        if s[0] == 1 and s[1] == 1 and math.isnan(data[0][0]):
            s = (0, 0)

        #first write length of record
        recordlength = 4 + 4 + 8 * s[0] * s[1] + 4 + 4
        #2 integers (32 bits) + the double matrix + code + matrix type
        if recordlength > 2**31:
            raise ValueError(
                'field %s cannot be marshalled because it is larger than 4^31 bytes!'
                % EnumToString(enum)[0])

        fid.write(
            struct.pack('i', recordlength)
        )  #2 integers (32 bits) + the double matrix + code + matrix type

        #write data code and matrix type:
        fid.write(struct.pack('i', FormatToCode(format)))
        fid.write(struct.pack('i', mattype))

        #now write matrix
        fid.write(struct.pack('i', s[0]))
        fid.write(struct.pack('i', s[1]))
        for i in range(s[0]):
            for j in range(s[1]):
                fid.write(struct.pack('d', float(
                    data[i]
                    [j])))  #get to the "c" convention, hence the transpose
        # }}}

    elif m.strcmpi(format, 'MatArray'):  # {{{

        #first get length of record
        recordlength = 4 + 4  #number of records + code
        for matrix in data:
            if isinstance(matrix, (bool, int, float)):
                matrix = numpy.array([matrix])
            elif isinstance(matrix, (list, tuple)):
                matrix = numpy.array(matrix).reshape(-1, 1)
            if numpy.ndim(matrix) == 1:
                if numpy.size(matrix):
                    matrix = matrix.reshape(numpy.size(matrix), 1)
                else:
                    matrix = matrix.reshape(0, 0)

            s = matrix.shape
            recordlength += 4 * 2 + s[0] * s[
                1] * 8  #row and col of matrix + matrix of doubles

        #write length of record
        fid.write(struct.pack('i', recordlength))

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #write data, first number of records
        fid.write(struct.pack('i', len(data)))

        #write each matrix:
        for matrix in data:
            if isinstance(matrix, (bool, int, float)):
                matrix = numpy.array([matrix])
            elif isinstance(matrix, (list, tuple)):
                matrix = numpy.array(matrix).reshape(-1, 1)
            if numpy.ndim(matrix) == 1:
                matrix = matrix.reshape(numpy.size(matrix), 1)

            s = matrix.shape
            fid.write(struct.pack('i', s[0]))
            fid.write(struct.pack('i', s[1]))
            for i in range(s[0]):
                for j in range(s[1]):
                    fid.write(struct.pack('d', float(matrix[i][j])))
        # }}}

    elif m.strcmpi(format, 'StringArray'):  # {{{

        #first get length of record
        recordlength = 4 + 4  #for length of array + code
        for string in data:
            recordlength += 4 + len(string)  #for each string

        #write length of record
        fid.write(struct.pack('i', recordlength))

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write length of string array
        fid.write(struct.pack('i', len(data)))

        #now write the strings
        for string in data:
            fid.write(struct.pack('i', len(string)))
            fid.write(struct.pack('%ds' % len(string), string))
        # }}}

    else:  # {{{
        raise TypeError(
            'WriteData error message: data type: %d not supported yet! (%s)' %
            (format, EnumToString(enum)[0]))
示例#24
0
文件: plotoptions.py 项目: pf4d/issm
    def buildlist(self, **kwargs):  #{{{

        for name, value in kwargs.items():
            self.rawlist[name] = value

        #get figure number
        self.figurenumber = rawoptions.getfieldvalue('figure', 1)
        rawoptions.removefield('figure', 0)

        #get number of subplots
        numberofplots = Counter(x for sublist in rawlist for x in sublist
                                if isinstance(x, str))['data']
        self.numberofplots = numberofplots

        #figure out whether alloptions flag is on
        if rawoptions.getfieldvalue('alloptions', 'off') is 'on':
            allflag = 1
        else:
            allflag = 0

        #initialize self.list (will need a list of dict's (or nested dict) for numberofplots>1)
        #self.list=defaultdict(dict)
        for i in range(numberofplots):
            self.list[i] = pairoptions.pairoptions()

        #process plot options
        for i in range(len(rawlist)):

            #if alloptions flag is on, apply to all plots
            if (allflag and 'data' not in rawlist[i][0]
                    and '#' not in rawlist[i][0]):

                for j in range(numberofplots):
                    self.list[j].addfield(rawlist[i][0], rawlist[i][1])

            elif '#' in rawlist[i][0]:

                #get subplots associated
                string = rawlist[i][0].split('#')
                plotnums = string[-1].split(',')
                field = string[0]

                #loop over plotnums
                for k in range(len(plotnums)):
                    plotnum = plotnums[k]

                    #Empty
                    if not plotnum:
                        continue

                        # '#all'
                    elif 'all' in plotnum:
                        for j in range(numberofplots):
                            self.list[j].addfield(field, rawlist[i][1])

                    # '#i-j'
                    elif '-' in plotnum:
                        nums = plotnum.split('-')
                        if len(nums) != 2: continue
                        if False in [x.isdigit() for x in nums]:
                            raise ValueError(
                                'error: in option i-j both i and j must be integers'
                            )
                        for j in range(int(nums[0]) - 1, int(nums[1])):
                            self.list[j].addfield(field, rawlist[i][1])

                    # Deal with #i
                    else:
                        #assign to subplot
                        if int(plotnum) > numberofplots:
                            raise ValueError(
                                'error: %s cannot be assigned %d which exceeds the number of subplots'
                                % (field, plotnum))
                        self.list[int(plotnum) - 1].addfield(
                            field, rawlist[i][1])
            else:

                #go through all subplots and assign key-value pairs
                j = 0
                while j <= numberofplots - 1:
                    if not self.list[j].exist(rawlist[i][0]):
                        self.list[j].addfield(rawlist[i][0], rawlist[i][1])
                        break
                    else:
                        j = j + 1
                if j + 1 > numberofplots:
                    print(("WARNING: too many instances of '%s' in options" %
                           rawlist[i][0]))
示例#25
0
文件: setmask.py 项目: pf4d/issm
def setmask(md, floatingicename, groundedicename, *args):
	"""
	SETMASK - establish boundaries between grounded and floating ice.

	   By default, ice is considered grounded. The contour floatingicename defines nodes 
	   for which ice is floating. The contour groundedicename defines nodes inside an floatingice, 
	   that are grounded (ie: ice rises, islands, etc ...)
	   All input files are in the Argus format (extension .exp).

	   Usage:
	      md=setmask(md,floatingicename,groundedicename)

	   Examples:
	      md=setmask(md,'all','');
	      md=setmask(md,'Iceshelves.exp','Islands.exp');
	"""
	#some checks on list of arguments
	print type(md)
	if not isinstance(md,model):
		raise TypeError("setmask error message")

	if len(args)%2:
		raise TypeError("odd number of arguments provided in setmask")

	#process options
	options=pairoptions.pairoptions(*args)

	#Get assigned fields
	x = md.mesh.x
	y = md.mesh.y
	elements = md.mesh.elements

	#Assign elementonfloatingice, elementongroundedice, vertexongroundedice and vertexonfloatingice. Only change at your own peril! This is synchronized heavily with the GroundingLineMigration module. {{{
	elementonfloatingice = FlagElements(md, floatingicename)
	elementongroundedice = FlagElements(md, groundedicename) 

	#Because groundedice nodes and elements can be included into an floatingice, we need to update. Remember, all the previous 
	#arrays come from domain outlines that can intersect one another: 

	elementonfloatingice = np.logical_and(elementonfloatingice,np.logical_not(elementongroundedice))
	elementongroundedice = np.logical_not(elementonfloatingice)

	#the order here is important. we choose vertexongroundedice as default on the grounding line.
	vertexonfloatingice = np.zeros(md.mesh.numberofvertices,'bool')
	vertexongroundedice = np.zeros(md.mesh.numberofvertices,'bool')
	vertexongroundedice[md.mesh.elements[np.nonzero(elementongroundedice),:]-1]=True
	vertexonfloatingice[np.nonzero(np.logical_not(vertexongroundedice))]=True
	#}}}

	#level sets
	md.mask.groundedice_levelset = -1.*np.ones(md.mesh.numberofvertices)
	md.mask.groundedice_levelset[md.mesh.elements[np.nonzero(elementongroundedice),:]-1]=1.

	if(len(args)):
		md.mask.ice_levelset = 1.*np.ones(md.mesh.numberofvertices)
		icedomainfile = options.getfieldvalue('icedomain','none')
		if not os.path.exists(icedomainfile):
			raise IOError("setmask error message: ice domain file '%s' not found." % icedomainfile)
		#use contourtomesh to set ice values inside ice domain
		vertexinsideicedomain,elementinsideicedomain=ContourToMesh(elements,x,y,icedomainfile,'node',1)
		md.mask.ice_levelset[np.nonzero(vertexinsideicedomain)[0]] = -1.
	else:
		md.mask.ice_levelset = -1.*np.ones(md.mesh.numberofvertices)

	return md
示例#26
0
文件: solve.py 项目: pf4d/issm
def solve(md, solutionstring, *args):
    """
	SOLVE - apply solution sequence for this model
 
	   Usage:
	      md=solve(md,solutionstring,varargin)
	      where varargin is a list of paired arguments of string OR enums
 
		solution types available comprise:
		 - 'Stressbalance'    or 'sb'
		 - 'Masstransport'    or 'mt'
		 - 'Thermal'          or 'th'
		 - 'Steadystate'      or 'ss'
		 - 'Transient'        or 'tr'
		 - 'Balancethickness' or 'mc'
		 - 'Balancevelocity'  or 'bv'
		 - 'BedSlope'         or 'bsl'
		 - 'SurfaceSlope'     or 'ssl'
		 - 'Hydrology'        or 'hy'
		 - 'DamageEvolution'  or 'da'
		 - 'Gia'              or 'gia'
		 - 'Sealevelrise'     or 'slr'

	   extra options:
        - loadonly : does not solve. only load results
		  - checkconsistency : 'yes' or 'no' (default is 'yes'), ensures checks on consistency of model
		  - restart: 'directory name (relative to the execution directory) where the restart file is located.
 
	   Examples:
	      md=solve(md,'Stressbalance');
         md=solve(md,'sb');
	"""

    #recover and process solve options
    if solutionstring.lower() == 'sb' or solutionstring.lower(
    ) == 'stressbalance':
        solutionstring = 'StressbalanceSolution'
    elif solutionstring.lower() == 'mt' or solutionstring.lower(
    ) == 'masstransport':
        solutionstring = 'MasstransportSolution'
    elif solutionstring.lower() == 'th' or solutionstring.lower() == 'thermal':
        solutionstring = 'ThermalSolution'
    elif solutionstring.lower() == 'st' or solutionstring.lower(
    ) == 'steadystate':
        solutionstring = 'SteadystateSolution'
    elif solutionstring.lower() == 'tr' or solutionstring.lower(
    ) == 'transient':
        solutionstring = 'TransientSolution'
    elif solutionstring.lower() == 'mc' or solutionstring.lower(
    ) == 'balancethickness':
        solutionstring = 'BalancethicknessSolution'
    elif solutionstring.lower() == 'bv' or solutionstring.lower(
    ) == 'balancevelocity':
        solutionstring = 'BalancevelocitySolution'
    elif solutionstring.lower() == 'bsl' or solutionstring.lower(
    ) == 'bedslope':
        solutionstring = 'BedSlopeSolution'
    elif solutionstring.lower() == 'ssl' or solutionstring.lower(
    ) == 'surfaceslope':
        solutionstring = 'SurfaceSlopeSolution'
    elif solutionstring.lower() == 'hy' or solutionstring.lower(
    ) == 'hydrology':
        solutionstring = 'HydrologySolution'
    elif solutionstring.lower() == 'da' or solutionstring.lower(
    ) == 'damageevolution':
        solutionstring = 'DamageEvolutionSolution'
    elif solutionstring.lower() == 'gia' or solutionstring.lower() == 'gia':
        solutionstring = 'GiaSolution'
    elif solutionstring.lower() == 'slr' or solutionstring.lower(
    ) == 'sealevelrise':
        solutionstring = 'SealevelriseSolution'
    else:
        raise ValueError("solutionstring '%s' not supported!" % solutionstring)
    options = pairoptions('solutionstring', solutionstring, *args)

    #recover some fields
    md.private.solution = solutionstring
    cluster = md.cluster
    if options.getfieldvalue('batch', 'no') == 'yes':
        batch = 1
    else:
        batch = 0

    #check model consistency
    if options.getfieldvalue('checkconsistency', 'yes') == 'yes':
        print "checking model consistency"
        ismodelselfconsistent(md)

    #First, build a runtime name that is unique
    restart = options.getfieldvalue('restart', '')
    if restart == 1:
        pass  #do nothing
    else:
        if restart:
            md.private.runtimename = restart
        else:
            if options.getfieldvalue('runtimename', True):
                c = datetime.datetime.now()
                md.private.runtimename = "%s-%02i-%02i-%04i-%02i-%02i-%02i-%i" % (
                    md.miscellaneous.name, c.month, c.day, c.year, c.hour,
                    c.minute, c.second, os.getpid())
            else:
                md.private.runtimename = md.miscellaneous.name

    #if running qmu analysis, some preprocessing of dakota files using models
    #fields needs to be carried out.
    if md.qmu.isdakota:
        md = preqmu(md, options)

    #Do we load results only?
    if options.getfieldvalue('loadonly', False):
        md = loadresultsfromcluster(md)
        return md

    #Write all input files
    marshall(md)  # bin file
    md.toolkits.ToolkitsFile(md.miscellaneous.name +
                             '.toolkits')  # toolkits file
    cluster.BuildQueueScript(md.private.runtimename, md.miscellaneous.name,
                             md.private.solution, md.settings.io_gather,
                             md.debug.valgrind, md.debug.gprof,
                             md.qmu.isdakota,
                             md.transient.isoceancoupling)  # queue file

    #Stop here if batch mode
    if options.getfieldvalue('batch', 'no') == 'yes':
        print 'batch mode requested: not launching job interactively'
        print 'launch solution sequence on remote cluster by hand'
        return md

    #Upload all required files:
    modelname = md.miscellaneous.name
    filelist = [
        modelname + '.bin ', modelname + '.toolkits ', modelname + '.queue '
    ]
    if md.qmu.isdakota:
        filelist.append(modelname + '.qmu.in')

    if not restart:
        cluster.UploadQueueJob(md.miscellaneous.name, md.private.runtimename,
                               filelist)

    #Launch job
    cluster.LaunchQueueJob(md.miscellaneous.name, md.private.runtimename,
                           filelist, restart, batch)

    #wait on lock
    if md.settings.waitonlock > 0:
        #we wait for the done file
        islock = waitonlock(md)
        if islock == 0:  #no results to be loaded
            print 'The results must be loaded manually with md=loadresultsfromcluster(md).'
        else:  #load results
            print 'loading results from cluster'
            md = loadresultsfromcluster(md)

    #post processes qmu results if necessary
    if md.qmu.isdakota:
        if not strncmpi(options['keep'], 'y', 1):
            shutil.rmtree('qmu' + str(os.getpid()))

    return md
示例#27
0
def WriteData(fid, prefix, *args):
    """
	WRITEDATA - write model field in binary file
 
	   Usage:
	      WriteData(fid,varargin)
	"""

    #process options
    options = pairoptions.pairoptions(*args)

    #Get data properties
    if options.exist('object'):
        #This is an object field, construct enum and data
        obj = options.getfieldvalue('object')
        fieldname = options.getfieldvalue('fieldname')
        classname = options.getfieldvalue(
            'class',
            str(type(obj)).rsplit('.')[-1].split("'")[0])
        name = options.getfieldvalue('name', prefix + '.' + fieldname)
        if options.exist('data'):
            data = options.getfieldvalue('data')
        else:
            data = getattr(obj, fieldname)
    else:
        #No processing required
        data = options.getfieldvalue('data')
        name = options.getfieldvalue('name')

    format = options.getfieldvalue('format')
    mattype = options.getfieldvalue('mattype', 0)  #only required for matrices
    timeserieslength = options.getfieldvalue('timeserieslength', -1)

    #Process sparse matrices
    #	if issparse(data),
    #		data=full(data);
    #	end

    #Scale data if necesarry
    if options.exist('scale'):
        scale = options.getfieldvalue('scale')
        if np.size(data) > 1:
            if np.size(data, 0) == timeserieslength:
                data = np.array(data)
                data[0:-1, :] = scale * data[0:-1, :]
            else:
                data = scale * data
        else:
            data = scale * data
    if np.size(data) > 1:
        if np.size(data, 0) == timeserieslength:
            yts = options.getfieldvalue('yts')
            data[-1, :] = yts * data[-1, :]

    #Step 1: write the enum to identify this record uniquely
    fid.write(struct.pack('i', len(name)))
    fid.write(struct.pack('%ds' % len(name), name))

    #Step 2: write the data itself.
    if m.strcmpi(format, 'Boolean'):  # {{{
        #		if len(data) !=1:
        #			raise ValueError('field %s cannot be marshalled as it has more than one element!' % name[0])

        #first write length of record
        fid.write(struct.pack('i', 4 + 4))  #1 bool (disguised as an int)+code

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write integer
        fid.write(struct.pack(
            'i', int(data)))  #send an int, not easy to send a bool
        # }}}

    elif m.strcmpi(format, 'Integer'):  # {{{
        #		if len(data) !=1:
        #			raise ValueError('field %s cannot be marshalled as it has more than one element!' % name[0])

        #first write length of record
        fid.write(struct.pack('i', 4 + 4))  #1 integer + code

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write integer
        fid.write(struct.pack('i', data))
        # }}}

    elif m.strcmpi(format, 'Double'):  # {{{
        #		if len(data) !=1:
        #			raise ValueError('field %s cannot be marshalled as it has more than one element!' % name[0])

        #first write length of record
        fid.write(struct.pack('i', 8 + 4))  #1 double+code

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write double
        fid.write(struct.pack('d', data))
        # }}}

    elif m.strcmpi(format, 'String'):  # {{{
        #first write length of record
        fid.write(struct.pack('i',
                              len(data) + 4 + 4))  #string + string size + code

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write string
        fid.write(struct.pack('i', len(data)))
        fid.write(struct.pack('%ds' % len(data), data))
        # }}}

    elif m.strcmpi(format, 'BooleanMat'):  # {{{

        if isinstance(data, bool):
            data = np.array([data])
        elif isinstance(data, (list, tuple)):
            data = np.array(data).reshape(-1, )
        if np.ndim(data) == 1:
            if np.size(data):
                data = data.reshape(np.size(data), )
            else:
                data = data.reshape(0, 0)

        #Get size
        s = data.shape
        #if matrix = NaN, then do not write anything
        if np.ndim(data) == 2 and np.product(s) == 1 and np.all(
                np.isnan(data)):
            s = (0, 0)

        #first write length of record
        fid.write(struct.pack(
            'i', 4 + 4 + 8 * np.product(s) + 4 +
            4))  #2 integers (32 bits) + the double matrix + code + matrix type

        #write data code and matrix type:
        fid.write(struct.pack('i', FormatToCode(format)))
        fid.write(struct.pack('i', mattype))

        #now write matrix
        if np.ndim(data) == 1:
            fid.write(struct.pack('i', s[0]))
            fid.write(struct.pack('i', 1))
            for i in xrange(s[0]):
                fid.write(struct.pack('d', float(
                    data[i])))  #get to the "c" convention, hence the transpose
        else:
            fid.write(struct.pack('i', s[0]))
            fid.write(struct.pack('i', s[1]))
            for i in xrange(s[0]):
                for j in xrange(s[1]):
                    fid.write(struct.pack('d', float(
                        data[i]
                        [j])))  #get to the "c" convention, hence the transpose
        # }}}

    elif m.strcmpi(format, 'IntMat'):  # {{{

        if isinstance(data, (int, long)):
            data = np.array([data])
        elif isinstance(data, (list, tuple)):
            data = np.array(data).reshape(-1, )
        if np.ndim(data) == 1:
            if np.size(data):
                data = data.reshape(np.size(data), )
            else:
                data = data.reshape(0, 0)

        #Get size
        s = data.shape
        #if matrix = NaN, then do not write anything
        if np.ndim(data) == 2 and np.product(s) == 1 and np.all(
                np.isnan(data)):
            s = (0, 0)

        #first write length of record
        fid.write(struct.pack(
            'i', 4 + 4 + 8 * np.product(s) + 4 +
            4))  #2 integers (32 bits) + the double matrix + code + matrix type

        #write data code and matrix type:
        fid.write(struct.pack('i', FormatToCode(format)))
        fid.write(struct.pack('i', mattype))

        #now write matrix
        if np.ndim(data) == 1:
            fid.write(struct.pack('i', s[0]))
            fid.write(struct.pack('i', 1))
            for i in xrange(s[0]):
                fid.write(struct.pack('d', float(
                    data[i])))  #get to the "c" convention, hence the transpose
        else:
            fid.write(struct.pack('i', s[0]))
            fid.write(struct.pack('i', s[1]))
            for i in xrange(s[0]):
                for j in xrange(s[1]):
                    fid.write(struct.pack('d', float(
                        data[i]
                        [j])))  #get to the "c" convention, hence the transpose
        # }}}

    elif m.strcmpi(format, 'DoubleMat'):  # {{{

        if isinstance(data, (bool, int, long, float)):
            data = np.array([data])
        elif isinstance(data, (list, tuple)):
            data = np.array(data).reshape(-1, )
        if np.ndim(data) == 1:
            if np.size(data):
                data = data.reshape(np.size(data), )
            else:
                data = data.reshape(0, 0)

        #Get size
        s = data.shape
        #if matrix = NaN, then do not write anything
        if np.ndim(data) == 1 and np.product(s) == 1 and np.all(
                np.isnan(data)):
            s = (0, 0)

        #first write length of record
        recordlength = 4 + 4 + 8 * np.product(s) + 4 + 4
        #2 integers (32 bits) + the double matrix + code + matrix type
        if recordlength > 4**31:
            raise ValueError(
                'field %s cannot be marshalled because it is larger than 4^31 bytes!'
                % enum)

        fid.write(
            struct.pack('i', recordlength)
        )  #2 integers (32 bits) + the double matrix + code + matrix type

        #write data code and matrix type:
        fid.write(struct.pack('i', FormatToCode(format)))
        fid.write(struct.pack('i', mattype))

        #now write matrix
        if np.ndim(data) == 1:
            fid.write(struct.pack('i', s[0]))
            fid.write(struct.pack('i', 1))
            for i in xrange(s[0]):
                fid.write(struct.pack('d', float(
                    data[i])))  #get to the "c" convention, hence the transpose
        else:
            fid.write(struct.pack('i', s[0]))
            fid.write(struct.pack('i', s[1]))
            for i in xrange(s[0]):
                for j in xrange(s[1]):
                    fid.write(struct.pack('d', float(
                        data[i]
                        [j])))  #get to the "c" convention, hence the transpose
        # }}}

    elif m.strcmpi(format, 'CompressedMat'):  # {{{

        if isinstance(data, (bool, int, long, float)):
            data = np.array([data])
        elif isinstance(data, (list, tuple)):
            data = np.array(data).reshape(-1, )
        if np.ndim(data) == 1:
            if np.size(data):
                data = data.reshape(np.size(data), )
            else:
                data = data.reshape(0, 0)

        #Get size
        s = data.shape
        if np.ndim(data) == 1:
            n2 = 1
        else:
            n2 = s[1]

        #if matrix = NaN, then do not write anything
        if np.ndim(data) == 1 and np.product(s) == 1 and np.all(
                np.isnan(data)):
            s = (0, 0)
            n2 = 0

        #first write length of record
        recordlength = 4 + 4 + 8 + 8 + 1 * (
            s[0] - 1
        ) * n2 + 8 * n2 + 4 + 4  #2 integers (32 bits) + the matrix + code + matrix type
        if recordlength > 4**31:
            raise ValueError(
                'field %s cannot be marshalled because it is larger than 4^31 bytes!'
                % enum)

        fid.write(struct.pack('i', recordlength)
                  )  #2 integers (32 bits) + the matrix + code + matrix type

        #write data code and matrix type:
        fid.write(struct.pack('i', FormatToCode(format)))
        fid.write(struct.pack('i', mattype))

        #Write offset and range
        A = data[0:s[0] - 1]
        offsetA = A.min()
        rangeA = A.max() - offsetA

        if rangeA == 0:
            A = A * 0
        else:
            A = (A - offsetA) / rangeA * 255.

        #now write matrix
        if np.ndim(data) == 1:
            fid.write(struct.pack('i', s[0]))
            fid.write(struct.pack('i', 1))
            fid.write(struct.pack('d', float(offsetA)))
            fid.write(struct.pack('d', float(rangeA)))
            for i in xrange(s[0] - 1):
                fid.write(struct.pack('B', int(A[i])))

            fid.write(struct.pack('d', float(
                data[s[0] -
                     1])))  #get to the "c" convention, hence the transpose

        elif np.product(s) > 0:
            fid.write(struct.pack('i', s[0]))
            fid.write(struct.pack('i', s[1]))
            fid.write(struct.pack('d', float(offsetA)))
            fid.write(struct.pack('d', float(rangeA)))
            for i in xrange(s[0] - 1):
                for j in xrange(s[1]):
                    fid.write(struct.pack('B', int(
                        A[i]
                        [j])))  #get to the "c" convention, hence the transpose

            for j in xrange(s[1]):
                fid.write(struct.pack('d', float(data[s[0] - 1][j])))

        # }}}

    elif m.strcmpi(format, 'MatArray'):  # {{{

        #first get length of record
        recordlength = 4 + 4  #number of records + code
        for matrix in data:
            if isinstance(matrix, (bool, int, long, float)):
                matrix = np.array([matrix])
            elif isinstance(matrix, (list, tuple)):
                matrix = np.array(matrix).reshape(-1, )
            if np.ndim(matrix) == 1:
                if np.size(matrix):
                    matrix = matrix.reshape(np.size(matrix), )
                else:
                    matrix = matrix.reshape(0, 0)

            s = matrix.shape
            recordlength += 4 * 2 + np.product(
                s) * 8  #row and col of matrix + matrix of doubles

        #write length of record
        fid.write(struct.pack('i', recordlength))

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #write data, first number of records
        fid.write(struct.pack('i', len(data)))

        #write each matrix:
        for matrix in data:
            if isinstance(matrix, (bool, int, long, float)):
                matrix = np.array([matrix])
            elif isinstance(matrix, (list, tuple)):
                matrix = np.array(matrix).reshape(-1, )
            if np.ndim(matrix) == 1:
                matrix = matrix.reshape(np.size(matrix), )

            s = matrix.shape
            if np.ndim(data) == 1:
                fid.write(struct.pack('i', s[0]))
                fid.write(struct.pack('i', 1))
                for i in xrange(s[0]):
                    fid.write(
                        struct.pack('d', float(matrix[i]))
                    )  #get to the "c" convention, hence the transpose
            else:
                fid.write(struct.pack('i', s[0]))
                fid.write(struct.pack('i', s[1]))
                for i in xrange(s[0]):
                    for j in xrange(s[1]):
                        fid.write(struct.pack('d', float(matrix[i][j])))
        # }}}

    elif m.strcmpi(format, 'StringArray'):  # {{{

        #first get length of record
        recordlength = 4 + 4  #for length of array + code
        for string in data:
            recordlength += 4 + len(string)  #for each string

        #write length of record
        fid.write(struct.pack('i', recordlength))

        #write data code:
        fid.write(struct.pack('i', FormatToCode(format)))

        #now write length of string array
        fid.write(struct.pack('i', len(data)))

        #now write the strings
        for string in data:
            fid.write(struct.pack('i', len(string)))
            fid.write(struct.pack('%ds' % len(string), string))
        # }}}

    else:  # {{{
        raise TypeError(
            'WriteData error message: data type: %d not supported yet! (%s)' %
            (format, enum))
示例#28
0
def solve(md, solutionenum, **kwargs):
    """
	SOLVE - apply solution sequence for this model
 
	   Usage:
	      md=solve(md,solutionenum,varargin)
	      where varargin is a list of paired arguments of string OR enums
 
	   solution types available comprise:
	      - StressbalanceSolutionEnum
	      - MasstransportSolutionEnum
	      - ThermalSolutionEnum
	      - SteadystateSolutionEnum
	      - TransientSolutionEnum
	      - BalancethicknessSolutionEnum
	      - BedSlopeSolutionEnum
	      - SurfaceSlopeSolutionEnum
	      - HydrologySolutionEnum
	      - FlaimSolutionEnum
 
	   extra options:
	      - loadonly : does not solve. only load results
		  - checkconsistency : 'yes' or 'no' (default is 'yes'), ensures checks on consistency of model
		  - restart: 'directory name (relative to the execution directory) where the restart file is located.
 
	   Examples:
	      md=solve(md,StressbalanceSolutionEnum);
	"""

    #recover and process solve options
    if EnumToString(solutionenum)[0][-8:] != 'Solution':
        raise ValueError("solutionenum '%s' not supported!" %
                         EnumToString(solutionenum)[0])
    options = pairoptions(solutionenum=solutionenum, **kwargs)

    #recover some fields
    md.private.solution = solutionenum
    cluster = md.cluster

    #check model consistency
    if m.strcmpi(options.getfieldvalue('checkconsistency', 'yes'), 'yes'):
        print("checking model consistency")
        if solutionenum == FlaimSolutionEnum():
            md.private.isconsistent = True
            md.mesh.checkconsistency(md, solutionenum)
            md.flaim.checkconsistency(md, solutionenum)
            if not md.private.isconsistent:
                raise RuntimeError("Model not consistent, see messages above.")
        else:
            ismodelselfconsistent(md)

    #First, build a runtime name that is unique
    restart = options.getfieldvalue('restart', '')
    if restart == 1:
        pass  #do nothing
    else:
        if restart:
            md.private.runtimename = restart
        else:
            if options.getfieldvalue('runtimename', True):
                c = datetime.datetime.now()
                md.private.runtimename = "%s-%02i-%02i-%04i-%02i-%02i-%02i-%i" % (
                    md.miscellaneous.name, c.month, c.day, c.year, c.hour,
                    c.minute, c.second, os.getpid())
            else:
                md.private.runtimename = md.miscellaneous.name

    #if running qmu analysis, some preprocessing of dakota files using models
    #fields needs to be carried out.
    if md.qmu.isdakota:
        md = preqmu(md, options)

    #flaim analysis
    if solutionenum == FlaimSolutionEnum():
        md = flaim_sol(md, options)
        [md.private.solution] = EnumToString(solutionenum)
        return md

    #Do we load results only?
    if options.getfieldvalue('loadonly', False):
        md = loadresultsfromcluster(md)
        return md

    #Write all input files
    marshall(md)  # bin file
    md.toolkits.ToolkitsFile(md.miscellaneous.name +
                             '.toolkits')  # toolkits file
    cluster.BuildQueueScript(md.private.runtimename, md.miscellaneous.name,
                             md.private.solution, md.settings.io_gather,
                             md.debug.valgrind, md.debug.gprof,
                             md.qmu.isdakota)  # queue file

    #Stop here if batch mode
    if m.strcmpi(options.getfieldvalue('batch', 'no'), 'yes'):
        print('batch mode requested: not launching job interactively')
        print('launch solution sequence on remote cluster by hand')
        return md

    #Upload all required files:
    modelname = md.miscellaneous.name
    filelist = [
        modelname + '.bin ', modelname + '.toolkits ', modelname + '.queue '
    ]
    if md.qmu.isdakota:
        filelist.append(modelname + '.qmu.in')

    if not restart:
        cluster.UploadQueueJob(md.miscellaneous.name, md.private.runtimename,
                               filelist)

    #Launch job
    cluster.LaunchQueueJob(md.miscellaneous.name, md.private.runtimename,
                           filelist, restart)

    #wait on lock
    if md.settings.waitonlock > 0:
        #we wait for the done file
        islock = waitonlock(md)
        if islock == 0:  #no results to be loaded
            print(
                'The results must be loaded manually with md=loadresultsfromcluster(md).'
            )
        else:  #load results
            print('loading results from cluster')
            md = loadresultsfromcluster(md)

    #post processes qmu results if necessary
    if md.qmu.isdakota:
        if not strncmpi(options['keep'], 'y', 1):
            shutil.rmtree('qmu' + str(os.getpid()))

    return md