added tign_four_pnts_interp subroutine
[wrffire.git] / other / convert_to_geogrid / namelist.py
blobf710c8fb025324db6d2f85582ed1c4e220d61a16
1 #!/usr/bin/python
2 """
3 Manipulates Fortran Namelists
5 Defines
6 Namelist class
8 TODO: == As a Stand alone program ==
9 Print info about Fortran Namelists
11 Usage: namelist.py -f FILENAME [-n NAMELIST [-p PARNAME]]
13 FILENAME: path/name of config file
14 NAMELIST: namelist name (since a file may contain many namelists)
15 PARNAME: Name of parameter to print value for
17 if NAMELIST is not provided,
18 print the list of namelist present in file in list form:
19 ['name1','name2',...]
20 if NAMELIST is provided (PARNAME not provided),
21 print all namelist param sin a "param=value" format, one per line
22 for multiple values of same param, print each one
23 as "param=value" format, one per line
24 if NAMELIST and PARNAME is provided,
25 if not specify, print all param in a "param=value" format
26 if specify and exist, print PARNAME's value only
27 for multiple values of same param, print each PARNAME's
28 values, one per line
30 This script is a generic Fortan namelist parser
31 and will recognize all namelist in a file with the following format,
32 and ignores the rest.
34 &namelistname
35 opt1 = value1
36 ...
38 """
40 __author__ = 'Stephane Chamberland (stephane.chamberland@ec.gc.ca)'
41 __version__ = '$Revision: 1.0 $'[11:-2]
42 __date__ = '$Date: 2006/09/05 21:16:24 $'
43 __copyright__ = 'Copyright (c) 2006 RPN'
44 __license__ = 'LGPL'
46 import sys
47 #sys.path.append("/usr/local/env/armnlib/modeles/SURF/python")
49 import re
51 from settings import Settings
53 # import sys
54 # import getopt
55 # import string
57 class Namelist(Settings):
58 """
59 Namelist class
60 Scan a Fortran Namelist file and put Section/Parameters into a dictionary
62 Intentiation:
64 foo = Namelist(NamelistFile)
66 where NamelistFile can be a filename, an URL or a string
68 Functions:
69 [Pending]
71 This is a generic Fortan namelist parser
72 it will recognize all namelist in a file with the following format,
73 and ignores the rest.
75 &namelistname
76 opt1 = value1
77 ...
79 """
81 def parse(self):
82 """Config file parser, called from the class initialization"""
83 varname = r'\b[a-zA-Z][a-zA-Z0-9_]*\b'
84 valueInt = re.compile(r'[+-]?[0-9]+')
85 valueReal = re.compile(r'[+-]?([0-9]+\.[0-9]*|[0-9]*\.[0-9]+)')
86 valueNumber = re.compile(r'\b(([\+\-]?[0-9]+)?\.)?[0-9]*([eE][-+]?[0-9]+)?')
87 valueBool = re.compile(r"(\.(true|false|t|f)\.)",re.I)
88 valueTrue = re.compile(r"(\.(true|t)\.)",re.I)
89 spaces = r'[\s\t]*'
90 quote = re.compile(r"[\s\t]*[\'\"]")
92 namelistname = re.compile(r"^[\s\t]*&(" + varname + r")[\s\t]*$")
93 paramname = re.compile(r"[\s\t]*(" + varname+r')[\s\t]*=[\s\t]*')
94 namlistend = re.compile(r"^" + spaces + r"/" + spaces + r"$")
96 #split sections/namelists
97 mynmlfile = {}
98 mynmlname = ''
99 for item in self.clean(self._setContent.split("\n"),cleancomma=1):
100 if re.match(namelistname,item):
101 mynmlname = re.sub(namelistname,r"\1",item)
102 mynmlfile[mynmlname] = {
103 'raw' : [],
104 'par' : [{}]
106 elif re.match(namlistend,item):
107 mynmlname = ''
108 else:
109 if mynmlname:
110 mynmlfile[mynmlname]['raw'].append(item)
112 #parse param in each section/namelist
113 for mynmlname in mynmlfile.keys():
114 #split strings
115 bb = []
116 for item in mynmlfile[mynmlname]['raw']:
117 bb.extend(self.splitstring(item))
118 #split comma and =
119 aa = []
120 for item in bb:
121 if not re.match(quote,item):
122 aa.extend(re.sub(r"[\s\t]*=",r" =\n",re.sub(r",+",r"\n",item)).split("\n"))
123 else:
124 aa.append(item)
125 del(bb)
126 aa = self.clean(aa,cleancomma=1)
128 myparname = ''
129 for item in aa:
130 if re.search(paramname,item):
131 myparname = re.sub(paramname,r"\1",item).lower()
132 mynmlfile[mynmlname]['par'][0][myparname] = []
133 elif paramname:
134 #removed quotes, spaces (then how to distinguish .t. of ".t."?)
135 if re.match(valueBool,item):
136 if re.match(valueTrue,item):
137 mynmlfile[mynmlname]['par'][0][myparname].append('.true.')
138 else:
139 mynmlfile[mynmlname]['par'][0][myparname].append('.false.')
140 else:
141 mynmlfile[mynmlname]['par'][0][myparname].append(re.sub(r"(^[\'\"]|[\'\"]$)",r"",item.strip()).strip())
142 return mynmlfile