Source code for pcse.fileinput.pcsefilereader

# -*- coding: utf-8 -*-
# Copyright (c) 2004-2014 Alterra, Wageningen-UR
# Allard de Wit (allard.dewit@wur.nl), April 2014
import os, sys
import inspect
import textwrap

[docs]class PCSEFileReader(dict): """Reader for parameter files in the PCSE format. This class is a replacement for the `CABOFileReader`. The latter can be used for reading parameter files in the CABO format, however this format has rather severe limitations: it only supports string, integer, float and array parameters. There is no support for specifying parameters with dates for example (other then specifying them as a string). The `PCSEFileReader` is a much more versatile tool for creating parameter files because it leverages the power of the python interpreter for processing parameter files through the `execfile` functionality in python. This means that anything that can be done in a python script can also be done in a PCSE parameter file. :param fname: parameter file to read and parse :returns: dictionary object with parameter key/value pairs. *Example* Below is an example of a parameter file 'parfile.pcse'. Parameters can be defined the 'CABO'-way, but also advanced functionality can be used by importing modules, defining parameters as dates or numpy arrays and even applying function on arrays (in this case `np.sin`):: \"\"\"This is the header of my parameter file. This file is derived from the following sources * dummy file for demonstrating the PCSEFileReader * contains examples how to leverage dates, arrays and functions, etc. \"\"\" import numpy as np import datetime as dt TSUM1 = 1100 TSUM2 = 900 DTSMTB = [ 0., 0., 5., 5., 20., 25., 30., 25.] AMAXTB = np.sin(np.arange(12)) cropname = "alfalfa" CROP_START_DATE = dt.date(2010,5,14) Can be read with the following statements:: >>>fileparameters = PCSEFileReader('parfile.pcse') >>>print fileparameters['TSUM1'] 1100 >>>print fileparameters['CROP_START_DATE'] 2010-05-14 >>>print fileparameters PCSE parameter file contents loaded from: D:\UserData\pcse_examples\parfile.pw This is the header of my parameter file. This file is derived from the following sources * dummy file for demonstrating the PCSEFileReader * contains examples how to leverage dates, arrays and functions, etc. DTSMTB: [0.0, 0.0, 5.0, 5.0, 20.0, 25.0, 30.0, 25.0] (<type 'list'>) CROP_START_DATE: 2010-05-14 (<type 'datetime.date'>) TSUM2: 900 (<type 'int'>) cropname: alfalfa (<type 'str'>) AMAXTB: [ 0. 0.84147098 0.90929743 0.14112001 -0.7568025 -0.95892427 -0.2794155 0.6569866 0.98935825 0.41211849 -0.54402111 -0.99999021] (<type 'numpy.ndarray'>) TSUM1: 1100 (<type 'int'>) """ def __init__(self, fname): dict.__init__(self) # Construct full path to parameter file and check file existence cwd = os.getcwd() self.fname_fp = os.path.normpath(os.path.join(cwd, fname)) if not os.path.exists(self.fname_fp): msg = "Could not find parameter file '%s'" % self.fname_fp raise RuntimeError(msg) # compile and execute the contents of the file bytecode = compile(open(self.fname_fp).read(), self.fname_fp, 'exec') exec(bytecode, {}, self) # Remove any members in self that are python modules keys = list(self.keys()) for k in keys: if inspect.ismodule(self[k]): self.pop(k) # If the file has a header (e.g. __doc__) store it. if "__doc__" in self: header = self.pop("__doc__") if len(header) > 0: self.header = header if self.header[-1] != "\n": self.header += "\n" else: self.header = None def __str__(self): printstr = "PCSE parameter file contents loaded from:\n" printstr += "%s\n\n" % self.fname_fp if self.header is not None: printstr += self.header for k in self: r = "%s: %s (%s)" % (k, self[k], type(self[k])) printstr += (textwrap.fill(r, subsequent_indent=" ") + "\n") return printstr