CMS 3D CMS Logo

Functions
mixture Namespace Reference

Functions

def getCompound (line)
 
def getMixture (line)
 
def getMixtures (inputFile)
 
def loadMaterialsFile (inputFile)
 
def main (argv)
 

Detailed Description

mixture.py replaces the functionality of mixture.f

Usage:

$ python3 mixture.py filename.in

Where `filename.in` contains a set of mixtures and its components:

The format for `filename.in` is as follows:

Each mixture description starts with a hash symbol (#) and contains
the following information in a single line:

 * Name (name of mixture of components)
 * GMIX name ()
 * MC Volume
 * MC Area

A mixture definition is followed by a set of compounds, which is the
set of components that the mixture is made from.

Each compound description starts with an asterisk (*) and contains
the following information:

 * Item number (An index for the list)
 * Comment (A human readable name for the material)
 * Material (Component name)
 * Volume
 * Multiplicity (How many times the material is in the mixture)
 * Type (see below)

Type stands for a classification of the Material using the following
convention:

 * SUP: Support
 * COL: Cooling
 * ELE: Electronics
 * CAB: Cables
 * SEN: Sensitive volumes

Each Material (component of the mixture) belongs to a single category.
`mixture.py` uses these information to compute how the mixture as a whole
contributes to each of the categories in terms of radiation length (x0)
and nuclear interaction length (l0) \lambda_{0}.

The radiation length or the nuclear interaction lenght become relevant
depending if we are talking about particles that interact with the detector
mainly throgh electromagnetic forces (x0) or either strong interaction or nuclear
forces (l0). Notice that these quantities are different and therefore the
contribution for each category will depend on them.

Any line in `filename.in` is therefore ignored unless it begins with
a hash or an asterisk.

Hardcoded in `mixture.py` are the files `mixed_materials.input` and
`pure_materials.input`. These files act as a database that provides
information about the compounds. From each compound defined in
`filename.in` `mixture.py` matches the content of `Material` with a
single element of the database and extracts the following information
(the format of the mentioned .input files):

 * Name (which should match with Material)
 * Weight (Atomic Mass) [g/mol]
 * Number (Atomic number)
 * Density (g/cm^3)
 * RadLen (Radiation lenght) (cm)
 * IntLen (Nuclear interaction lenght) (cm)

With these information `material.py` computes for each mixture:

 * The radiation lenght for the mixture
 * The nuclear interaction lenght for the mixture
 * The mixture density
 * The mixture volume
 * The total weight
 * The relative contribution in each categorio on x0 and l0
 * Normalized quantities based on MC Volume and MC Area values

As well for the compounds:

 * The relative volume within the mixture
 * The relative weight
 * The relative radiation lenght
 * The relative nuclear interaction length

Function Documentation

def mixture.getCompound (   line)

Definition at line 108 of file mixture.py.

References objects.autophobj.float, and createfilelist.int.

Referenced by getMixtures().

108 def getCompound(line) :
109  compound = re.search(
110  r'^\*\s*(?P<Index>[0-9]+)\s+"(?P<Comment>[^"]+)"\s+"(?P<Material>[^"]+)"\s+(?P<Volume>[0-9.Ee\-+]+)\s+(?P<Mult>[0-9.]+)\s+(?P<Type>[^ ]{3})',
111  line
112  )
113  return {
114  'item_number' : int(compound.group("Index")),
115  'comment' : compound.group("Comment"),
116  'material' : compound.group("Material"),
117  'volume' : float(compound.group("Volume")),
118  'multiplicity' : float(compound.group("Mult")),
119  'category' : compound.group("Type"),
120  }
121 
def getCompound(line)
Definition: mixture.py:108
def mixture.getMixture (   line)

Definition at line 95 of file mixture.py.

References objects.autophobj.float.

Referenced by getMixtures().

95 def getMixture(line) :
96  mixture = re.search(
97  r'^#\s*"(?P<MixtureName>[^"]+)"\s+"(?P<GMIXName>[^"]+)"\s+(?P<MCVolume>[0-9.Ee\-+]+)\s+(?P<MCArea>[0-9.Ee\-+]+)',
98  line
99  )
100  return {
101  'mixture_name' : mixture.group("MixtureName"),
102  'gmix_name' : mixture.group("GMIXName"),
103  'mc_volume' : float(mixture.group("MCVolume")),
104  'mc_area' : float(mixture.group("MCArea")),
105  }
106 
107 
def getMixture(line)
Definition: mixture.py:95
def mixture.getMixtures (   inputFile)
Returns a `dict` of Mixtures. Each
mixture contains a list of compounds.

Definition at line 122 of file mixture.py.

References mps_setup.append, cmsPerfStripChart.dict, getCompound(), and getMixture().

Referenced by main().

122 def getMixtures(inputFile) :
123 
124  """
125  Returns a `dict` of Mixtures. Each
126  mixture contains a list of compounds.
127  """
128 
129  inFile = open(inputFile,"r")
130 
131  mixtures = []
132  mixture = {}
133 
134  counter = 0
135  prevCounter = 0
136 
137  for line in inFile.readlines():
138 
139  if line[0] == "#":
140  if mixture:
141  mixtures.append(dict(mixture)) #Just to make a copy
142  mixture.clear()
143  mixture = getMixture(line)
144  mixture.update({ 'components' : [] })
145 
146  if line[0] == "*":
147  mixture['components'].append(dict(getCompound(line)))
148 
149  inFile.close()
150 
151  return mixtures
152 
def getCompound(line)
Definition: mixture.py:108
def getMixtures(inputFile)
Definition: mixture.py:122
def getMixture(line)
Definition: mixture.py:95
def mixture.loadMaterialsFile (   inputFile)

Definition at line 153 of file mixture.py.

References objects.autophobj.float.

Referenced by main().

153 def loadMaterialsFile(inputFile):
154 
155  mixMatFile = open(inputFile,"r")
156 
157  mixMats = []
158 
159  for line in mixMatFile.readlines():
160 
161  if line[0] == '"':
162  mixMat = re.search(
163  r'^"(?P<name>[^"]+)"\s+(?P<weight>[0-9.Ee-]+)\s+(?P<number>[0-9.Ee-]+)\s+(?P<density>[0-9.Ee-]+)\s+(?P<x0>[0-9.Ee-]+)\s+(?P<l0>[0-9Ee.-]+)',
164  line
165  )
166 
167  mixMats.append({
168  "name" : mixMat.group("name"),
169  "weight" : float(mixMat.group("weight")),
170  "number" : float(mixMat.group("number")),
171  "density" : float(mixMat.group("density")),
172  "x0" : float(mixMat.group("x0")),
173  "l0" : float(mixMat.group("l0")),
174  })
175 
176  return mixMats
177 
def loadMaterialsFile(inputFile)
Definition: mixture.py:153
def mixture.main (   argv)

Definition at line 178 of file mixture.py.

References popcon2dropbox.copy(), getMixtures(), loadMaterialsFile(), edm.print(), and str.

178 def main(argv):
179 
180  listOfMixtures = getMixtures(str(argv[1]))
181 
182  fname = re.search("(?P<filename>[a-zA-Z0-9_]+)",str(argv[1]))
183 
184  fname = str(fname.group("filename"))
185  radLenFile = open(fname + ".x0","w");
186  intLenFile = open(fname + ".l0","w");
187 
188  listOfMixedMaterials = loadMaterialsFile(inputFile="mixed_materials.input")
189  listOfPureMaterials = loadMaterialsFile(inputFile="pure_materials.input")
190  listOfMaterials = listOfMixedMaterials + listOfPureMaterials
191 
192  dfAllMaterials = pd.DataFrame(listOfMaterials)
193 
194  for index in range(len(listOfMixtures)):
195 
196  gmixName = listOfMixtures[index]["gmix_name"]
197  print("================================")
198  print(gmixName)
199 
200  components = pd.DataFrame(listOfMixtures[index]['components'])
201 
202  components["volume"] = components["multiplicity"]*components["volume"]
203  totalVolume = sum(
204  components["volume"]
205  )
206 
207  components["percentVolume"] = components["volume"] / totalVolume
208 
209  components = pd.merge(
210  components,
211  dfAllMaterials[["name","density","x0","l0"]],
212  left_on="material",
213  right_on="name"
214  )
215 
216  components["weight"] = components["density"] * components["volume"]
217 
218  totalDensity = sum(
219  components["percentVolume"] * components["density"]
220  )
221 
222  totalWeight = totalDensity * totalVolume
223 
224  components["percentWeight"] = (
225  components["density"] * components["volume"] / totalWeight
226  )
227 
228  components["ws"] = (
229  components["percentWeight"] / (components["density"]*components["x0"])
230  )
231 
232  components["ws2"] = (
233  components["percentWeight"] / (components["density"]*components["l0"])
234  )
235 
236  totalRadLen = 1 / ( sum(components["ws"]) * totalDensity )
237 
238  totalIntLen = 1/ ( sum(components["ws2"]) * totalDensity )
239 
240  components["percentRadLen"] = (
241  components["ws"] * totalRadLen * totalDensity
242  )
243 
244  components["percentIntLen"] = (
245  components["ws2"] * totalIntLen * totalDensity
246  )
247 
248  displayDf = components[[
249  "comment",
250  "material","volume",
251  "percentVolume","percentWeight",
252  "density","weight","x0","percentRadLen",
253  "l0","percentIntLen"
254  ]].copy()
255 
256  displayDf["percentVolume"] *= 100.
257  displayDf["percentWeight"] *= 100.
258  displayDf["percentRadLen"] *= 100.
259  displayDf["percentIntLen"] *= 100.
260 
261  displayDf = displayDf.rename(
262  columns = {
263  "comment" : "Component",
264  "material" : "Material",
265  "volume" : "Volume [cm^3]",
266  "percentVolume" : "Volume %",
267  "density" : "Density",
268  "weight" : "Weight",
269  "percentWeight" : "Weight %",
270  "x0" : "X_0 [cm]",
271  "percentRadLen" : "X_0 %",
272  "l0": "lambda_0 [cm]",
273  "percentIntLen" : "lambda_0 %",
274  }
275  )
276 
277  print(displayDf)
278 
279 
280  # Normalized vars:
281 
282  mcVolume = listOfMixtures[index]["mc_volume"]
283  mcArea = listOfMixtures[index]["mc_area"]
284  normalizationFactor = -1.
285 
286  if mcVolume > 0:
287  normalizationFactor = totalVolume / mcVolume
288  else:
289  normalizationFactor = 1.
290 
291  normalizedDensity = totalDensity * normalizationFactor
292  normalizedRadLen = totalRadLen / normalizationFactor
293  normalizedIntLen = totalIntLen / normalizationFactor
294 
295  percentRadL = -1.
296  percentIntL = -1.
297 
298  if mcArea > 0:
299  percentRadL = mcVolume / (mcArea*normalizedRadLen)
300  percentIntL = mcVolume / (mcArea*normalizedIntLen)
301 
302  pSupRadLen = 0.
303  pSenRadLen = 0.
304  pCabRadLen = 0.
305  pColRadLen = 0.
306  pEleRadLen = 0.
307 
308  pSupIntLen = 0.
309  pSenIntLen = 0.
310  pCabIntLen = 0.
311  pColIntLen = 0.
312  pEleIntLen = 0.
313 
314  for index, component in components.iterrows():
315  catg = component["category"]
316  prl = component["percentRadLen"]
317  irl = component["percentIntLen"]
318  if catg.upper() == "SUP":
319  pSupRadLen += prl
320  pSupIntLen += irl
321  elif catg.upper() == "SEN":
322  pSenRadLen += prl
323  pSenIntLen += irl
324  elif catg.upper() == "CAB":
325  pCabRadLen += prl
326  pCabIntLen += irl
327  elif catg.upper() == "COL":
328  pColRadLen += prl
329  pColIntLen += irl
330  elif catg.upper() == "ELE":
331  pEleRadLen += prl
332  pEleIntLen += irl
333 
334  print("================================")
335  print("Mixture Density [g/cm^3]: " , totalDensity)
336  print("Norm. mixture density [g/cm^3]: ", normalizedDensity)
337  print("Mixture Volume [cm^3]: ", totalVolume)
338  print("MC Volume [cm^3]: ", mcVolume)
339  print("MC Area [cm^2]: ", mcArea)
340  print("Normalization Factor: ", normalizationFactor)
341  print("Mixture x0 [cm]: ", totalRadLen)
342  print("Norm. Mixture x0 [cm]: ", normalizedRadLen)
343  if mcArea > 0 :
344  print("Norm. Mixture x0 [%]: ", 100. * percentRadL)
345  print("Mixture l0 [cm]: ", totalIntLen)
346  print("Norm. Mixture l0 [cm]: ", normalizedIntLen)
347  if mcArea > 0 :
348  print("Norm. Mixture l0 [%]: ", 100. * percentIntL)
349  print("Total Weight [g]: ", totalWeight)
350 
351  print("================================")
352  print("X0 Contribution: ")
353  print("Support :", pSupRadLen)
354  print("Sensitive :", pSenRadLen)
355  print("Cables :", pCabRadLen)
356  print("Cooling :", pColRadLen)
357  print("Electronics :", pEleRadLen)
358 
359  print("================================")
360  print("l0 Contribution: ")
361  print("Support :", pSupIntLen)
362  print("Sensitive :", pSenIntLen)
363  print("Cables :", pCabIntLen)
364  print("Cooling :", pColIntLen)
365  print("Electronics :", pEleIntLen)
366 
367  radLenFile.write("{0:<50}{1:>8}{2:>8}{3:>8}{4:>8}{5:>8}\n".format(
368  gmixName,
369  round(pSupRadLen,3), round(pSenRadLen,3),
370  round(pCabRadLen,3), round(pColRadLen,3),
371  round(pEleRadLen,3)
372  ))
373 
374  intLenFile.write("{0:<50}{1:>8}{2:>8}{3:>8}{4:>8}{5:>8}\n".format(
375  gmixName,
376  round(pSupIntLen,3), round(pSenIntLen,3),
377  round(pCabIntLen,3), round(pColIntLen,3),
378  round(pEleIntLen,3)
379  ))
380 
381  radLenFile.close()
382  intLenFile.close()
383 
def copy(args, dbName)
S & print(S &os, JobReport::InputFile const &f)
Definition: JobReport.cc:66
def getMixtures(inputFile)
Definition: mixture.py:122
def main(argv)
Definition: mixture.py:178
def loadMaterialsFile(inputFile)
Definition: mixture.py:153
#define str(s)