def write_grdecl(self, ecl_kw, pyfile, special_header=None, default_value=0): """ Writes an EclKW instance as an ECLIPSE grdecl formatted file. The input argument @ecl_kw must be an EclKW instance of size nactive or nx*ny*nz. If the size is nactive the inactive cells will be filled with @default_value; hence the function will always write nx*ny*nz elements. The data in the @ecl_kw argument can be of type integer, float, double or bool. In the case of bool the default value must be specified as 1 (True) or 0 (False). The input argument @pyfile should be a valid python filehandle opened for writing; i.e. pyfile = open("PORO.GRDECL" , "w") grid.write_grdecl( poro_kw , pyfile , default_value = 0.0) grid.write_grdecl( permx_kw , pyfile , default_value = 0.0) pyfile.close() """ if ecl_kw.size == self.nactive or ecl_kw.size == self.size: cfile = CFILE(pyfile) cfunc.fwrite_grdecl(self, ecl_kw, special_header, cfile, default_value) else: raise ValueError( "Keyword: %s has invalid size(%d), must be either nactive:%d or nx*ny*nz:%d" % (ecl_kw.name, ecl_kw.size, self.nactive, self.size))
def fseek_grdecl(cls, fileH, kw, rewind=False): """ Will search through the open file and look for string @kw. If the search succeeds the function will return and the file pointer will be positioned at the start of the kw, if the search fails the function will return false and the file pointer will be repositioned at the position it had prior to the call. Only @kw instances which are found at the beginning of a line (with optional leading space characters) are considered, i.e. searching for the string PERMX in the cases below will fail: -- PERMX EQUIL PERMX / The function will start searching from the current position in the file and forwards, if the optional argument @rewind is true the function rewind to the beginning of the file and search from there after the initial search. """ cfile = CFILE(fileH) return cfunc.fseek_grdecl(kw, rewind, cfile)
def fprint(self, fileH, fmt="%g "): """Will print ASCII representation of matrix. The fileH argument should point to an open Python filehandle. If you supply a fmt string it is important that it contains a separator, otherwise you might risk that elements overlap in the output. For the matrix: [0 1 2] m = [3 4 5] [6 7 8] The code: with open("matrix.txt" , "w") as f: m.fprintf( f ) The file 'matrix.txt' will look like: 0 1 2 3 4 5 6 7 8 """ self._fprint(fmt, CFILE(fileH))
def save_grdecl(self, pyfile): """ Will write the the grid content as grdecl formatted keywords. Will only write the main grid. """ cfile = CFILE(pyfile) cfunc.fprintf_grdecl(self, cfile)
def dumpCSVLine(self, time, keywords, pfile): """ Will dump a csv formatted line of the keywords in @keywords, evaluated at the intertpolated time @time. @pfile should point to an open Python file handle. """ cfile = CFILE(pfile) ctime = CTime(time) EclSum._dump_csv_line(self, ctime, keywords, cfile)
def printf(self, fmt=None, name=None, stream=sys.stdout): """ See also the str() method which returns string representantion of the vector. """ cfile = CFILE(stream) if not fmt: fmt = self.default_format self.cNamespace().fprintf(self, cfile, name, fmt)
def test_cfile(self): with TestAreaContext("cfile_tests") as test_area: with open("test", "w") as f: f.write("some content") with open("test", "r") as f: cfile = CFILE(f) self.assertEqual(fileno(cfile), f.fileno())
def eclWrite(self , path , filename , export_file = None): if not path is None: if not os.path.isdir(path): raise IOError("The directory:%s does not exist" % path) if export_file: with open(export_file , "w") as fileH: GenKw.cNamespace().ecl_write(self , path , filename , CFILE( fileH )) else: GenKw.cNamespace().ecl_write(self , path , filename , None )
def fprintf_data(self, file, fmt=None): """ Will print the keyword data formatted to file. The @file argument should be a python file handle to a file opened for writing. The @fmt argument is used as fprintf() format specifier, observe that the format specifier should include a separation character between the elements. If no @fmt argument is supplied the default str_fmt specifier is used for every element, separated by a newline. In the case of boolean data the function will print o and 1 for False and True respectively. For string data the function will print the data as 8 characters long string with blank padding on the right. """ if fmt is None: fmt = self.str_fmt + "\n" cfile = CFILE(file) cfunc.fprintf_data(self, fmt, cfile)
def write_grdecl(self, file): """ Will write keyword in GRDECL format. This method will write the current keyword in GRDECL format, the @file argument must be a Python file handle to an already opened file. In the example below we load the porosity from an existing GRDECL file, set all poro values below 0.05 to 0.00 and write back an updated GRDECL file. poro = ecl.EclKW.load_grdecl( open("poro1.grdecl" , "r") , "PORO" ) grid = ecl.EclGrid( "ECLIPSE.EGRID" ) reg = ecl.EclRegion( grid , False ) reg.select_below( poro , 0.05 ) poro.assign( 0.0 , mask = reg ) fileH = open( "poro2.grdecl" , "w") poro.write_grdecl( fileH ) fileH.close() """ cfile = CFILE(file) cfunc.fprintf_grdecl(self, cfile)
def read_grdecl(cls, fileH, kw, strict=True, ecl_type=None): """ Function to load an EclKW instance from a grdecl formatted filehandle. This constructor can be used to load an EclKW instance from a grdecl formatted file; the input files for petrophysical properties are typically given as grdecl files. The @file argument should be a Python filehandle to an open file. The @kw argument should be the keyword header you are searching for, e.g. "PORO" or "PVTNUM"[1], the method will then search forward through the file to look for this @kw. If the keyword can not be found the method will return None. The searching will start from the current position in the file; so if you want to reposition the file pointer you should use the seek() method of the file object first. Observe that there is a strict 8 character limit on @kw - altough you could in principle use an arbitrary external program to create grdecl files with more than 8 character length headers, this implementation will refuse to even try loading them. In that case you will have to rename the keywords in your file - sorry. A TypeError exception will be raised if @kw has more than 8 characters. The implementation in ert can read integer and float type keywords from grdecl files; however the grdecl files have no datatype header, and it is impossible to determine the type reliably by inspection. Hence the type must be known when reading the file. The algorithm for specifying type, in order of presedence, is as follows: 1. The optional argument @ecl_type can be used to specify the type: special_int_kw = EclKW.read_grdecl( fileH , 'INTKW' , ecl_type = ECL_INT_TYPE ) If ecl_type is different from ECL_INT_TYPE or ECL_FLOAT_TYPE a TypeError exception will be raised. If ecl_type == None (the default), the method will continue to point 2. or 3. to determine the correct type. 2. If the keyword is included in the set built in set 'int_kw_set' the type will be ECL_INT_TYPE. pvtnum_kw = EclKW.read_grdecl( fileH , 'PVTNUM' ) Observe that (currently) no case conversions take place when checking the 'int_kw_set'. The current built in set is accesible through the int_kw property. 3. Otherwise the default is float, i.e. ECL_FLOAT_TYPE. poro_kw = EclKW.read_grdecl( fileH , 'PORO') Observe that since the grdecl files are quite weakly structured it is difficult to verify the integrity of the files, malformed input might therefor pass unnoticed before things blow up at a later stage. [1]: It is possible, but not recommended, to pass in None for @kw, in which case the method will load the first keyword it finds in the file. """ cfile = CFILE(fileH) if kw: if len(kw) > 8: raise TypeError( "Sorry keyword:%s is too long, must be eight characters or less." % kw) if ecl_type is None: if cls.int_kw_set.__contains__(kw): ecl_type = EclTypeEnum.ECL_INT_TYPE else: ecl_type = EclTypeEnum.ECL_FLOAT_TYPE if not ecl_type in [ EclTypeEnum.ECL_FLOAT_TYPE, EclTypeEnum.ECL_INT_TYPE ]: raise TypeError("The type:%d is invalid when loading keyword:%s" % (ecl_type, kw)) c_ptr = cfunc.load_grdecl(cfile, kw, strict, ecl_type) if c_ptr: obj = cls() obj.init_cobj(c_ptr, cfunc.free) obj.__init() return obj else: return None
def exportParameters(self, file_name): """ @type: str """ with open(file_name , "w") as py_file: cfile = CFILE( py_file ) GenKw.cNamespace().export_parameters(self, cfile)
def test_cfile_error(self): with self.assertRaises(TypeError): cfile = CFILE("some text")