Package models :: Module check_param_card
[hide private]
[frames] | no frames]

Source Code for Module models.check_param_card

   1  from __future__ import division 
   2   
   3  import itertools 
   4  import xml.etree.ElementTree as ET 
   5  import math 
   6  import StringIO 
   7  import os 
   8  import re 
   9  import shutil 
  10  import logging 
  11  import random 
  12   
  13  logger = logging.getLogger('madgraph.models') # -> stdout 
  14   
  15  try: 
  16      import madgraph.iolibs.file_writers as file_writers 
  17      import madgraph.various.misc as misc     
  18  except: 
  19      import internal.file_writers as file_writers 
  20      import internal.misc as misc 
  21   
  22  pjoin = os.path.join  
23 24 -class InvalidParamCard(Exception):
25 """ a class for invalid param_card """ 26 pass
27
28 -class Parameter (object):
29 """A class for a param_card parameter""" 30
31 - def __init__(self, param=None, block=None, lhacode=None, value=None, comment=None):
32 """Init the parameter""" 33 34 self.format = 'float' 35 if param: 36 block = param.lhablock 37 lhacode = param.lhacode 38 value = param.value 39 comment = param.comment 40 format = param.format 41 42 self.lhablock = block 43 if lhacode: 44 self.lhacode = lhacode 45 else: 46 self.lhacode = [] 47 self.value = value 48 self.comment = comment
49
50 - def set_block(self, block):
51 """ set the block name """ 52 53 self.lhablock = block
54
55 - def load_str(self, text):
56 """ initialize the information from a str""" 57 58 if '#' in text: 59 data, self.comment = text.split('#',1) 60 else: 61 data, self.comment = text, "" 62 63 64 data = data.split() 65 if any(d.startswith('scan') for d in data): 66 position = [i for i,d in enumerate(data) if d.startswith('scan')][0] 67 data = data[:position] + [' '.join(data[position:])] 68 if not len(data): 69 return 70 try: 71 self.lhacode = tuple([int(d) for d in data[:-1]]) 72 except Exception: 73 self.lhacode = tuple([int(d) for d in data[:-1] if d.isdigit()]) 74 self.value= ' '.join(data[len(self.lhacode):]) 75 else: 76 self.value = data[-1] 77 78 # convert to number when possible 79 try: 80 self.value = float(self.value) 81 except: 82 self.format = 'str' 83 pass 84 else: 85 if self.lhablock == 'modsel': 86 self.format = 'int' 87 self.value = int(self.value)
88
89 - def load_decay(self, text):
90 """ initialize the decay information from a str""" 91 92 if '#' in text: 93 data, self.comment = text.split('#',1) 94 else: 95 data, self.comment = text, "" 96 97 98 data = data.split() 99 if not len(data): 100 return 101 self.lhacode = [int(d) for d in data[2:]] 102 self.lhacode.sort() 103 self.lhacode = tuple([len(self.lhacode)] + self.lhacode) 104 105 self.value = float(data[0]) 106 self.format = 'decay_table'
107
108 - def __str__(self, precision=''):
109 """ return a SLAH string """ 110 111 112 format = self.format 113 if self.format == 'float': 114 try: 115 value = float(self.value) 116 except: 117 format = 'str' 118 self.comment = self.comment.strip() 119 if not precision: 120 precision = 6 121 122 if format == 'float': 123 if self.lhablock == 'decay' and not isinstance(self.value,basestring): 124 return 'DECAY %s %.{0}e # %s'.format(precision) % (' '.join([str(d) for d in self.lhacode]), self.value, self.comment) 125 elif self.lhablock == 'decay': 126 return 'DECAY %s Auto # %s' % (' '.join([str(d) for d in self.lhacode]), self.comment) 127 elif self.lhablock and self.lhablock.startswith('qnumbers'): 128 return ' %s %i # %s' % (' '.join([str(d) for d in self.lhacode]), int(self.value), self.comment) 129 else: 130 return ' %s %.{0}e # %s'.format(precision) % (' '.join([str(d) for d in self.lhacode]), self.value, self.comment) 131 elif format == 'int': 132 return ' %s %i # %s' % (' '.join([str(d) for d in self.lhacode]), int(self.value), self.comment) 133 elif format == 'str': 134 if self.lhablock == 'decay': 135 return 'DECAY %s %s # %s' % (' '.join([str(d) for d in self.lhacode]),self.value, self.comment) 136 return ' %s %s # %s' % (' '.join([str(d) for d in self.lhacode]), self.value, self.comment) 137 elif self.format == 'decay_table': 138 return ' %e %s # %s' % ( self.value,' '.join([str(d) for d in self.lhacode]), self.comment) 139 elif self.format == 'int': 140 return ' %s %i # %s' % (' '.join([str(d) for d in self.lhacode]), int(self.value), self.comment) 141 else: 142 if self.lhablock == 'decay': 143 return 'DECAY %s %d # %s' % (' '.join([str(d) for d in self.lhacode]), self.value, self.comment) 144 else: 145 return ' %s %d # %s' % (' '.join([str(d) for d in self.lhacode]), self.value, self.comment)
146
147 148 -class Block(list):
149 """ list of parameter """ 150
151 - def __init__(self, name=None):
152 if name: 153 self.name = name.lower() 154 else: 155 self.name = name 156 self.scale = None 157 self.comment = '' 158 self.decay_table = {} 159 self.param_dict={} 160 list.__init__(self)
161
162 - def get(self, lhacode, default=None):
163 """return the parameter associate to the lhacode""" 164 if not self.param_dict: 165 self.create_param_dict() 166 167 if isinstance(lhacode, int): 168 lhacode = (lhacode,) 169 170 try: 171 return self.param_dict[tuple(lhacode)] 172 except KeyError: 173 if default is None: 174 raise KeyError, 'id %s is not in %s' % (tuple(lhacode), self.name) 175 else: 176 return Parameter(block=self, lhacode=lhacode, value=default, 177 comment='not define')
178
179 - def rename_keys(self, change_keys):
180 181 182 for old_key, new_key in change_keys.items(): 183 184 assert old_key in self.param_dict 185 param = self.param_dict[old_key] 186 del self.param_dict[old_key] 187 self.param_dict[new_key] = param 188 param.lhacode = new_key
189 190
191 - def remove(self, lhacode):
192 """ remove a parameter """ 193 list.remove(self, self.get(lhacode)) 194 # update the dictionary of key 195 return self.param_dict.pop(tuple(lhacode))
196
197 - def __eq__(self, other, prec=1e-4):
198 """ """ 199 200 if isinstance(other, str) and ' ' not in other: 201 return self.name.lower() == other.lower() 202 203 204 if len(self) != len(other): 205 return False 206 207 return not any(abs(param.value-other.param_dict[key].value)> prec * abs(param.value) 208 for key, param in self.param_dict.items())
209
210 - def __ne__(self, other, prec=1e-4):
211 return not self.__eq__(other, prec)
212
213 - def append(self, obj):
214 215 assert isinstance(obj, Parameter) 216 if not hasattr(self, 'name'): #can happen if loeaded from pickle 217 self.__init__(obj.lhablock) 218 assert not obj.lhablock or obj.lhablock == self.name 219 220 #The following line seems/is stupid but allow to pickle/unpickle this object 221 #this is important for madspin (in gridpack mode) 222 if not hasattr(self, 'param_dict'): 223 self.param_dict = {} 224 225 if tuple(obj.lhacode) in self.param_dict: 226 if self.param_dict[tuple(obj.lhacode)].value != obj.value: 227 raise InvalidParamCard, '%s %s is already define to %s impossible to assign %s' % \ 228 (self.name, obj.lhacode, self.param_dict[tuple(obj.lhacode)].value, obj.value) 229 return 230 list.append(self, obj) 231 # update the dictionary of key 232 self.param_dict[tuple(obj.lhacode)] = obj
233
234 - def create_param_dict(self):
235 """create a link between the lhacode and the Parameter""" 236 for param in self: 237 self.param_dict[tuple(param.lhacode)] = param 238 239 return self.param_dict
240
241 - def def_scale(self, scale):
242 """ """ 243 self.scale = scale
244
245 - def load_str(self, text):
246 "set inforamtion from the line" 247 248 if '#' in text: 249 data, self.comment = text.split('#',1) 250 else: 251 data, self.comment = text, "" 252 253 data = data.lower() 254 data = data.split() 255 self.name = data[1] # the first part of data is model 256 if len(data) == 3: 257 if data[2].startswith('q='): 258 #the last part should be of the form Q= 259 self.scale = float(data[2][2:]) 260 elif self.name == 'qnumbers': 261 self.name += ' %s' % data[2] 262 elif len(data) == 4 and data[2] == 'q=': 263 #the last part should be of the form Q= 264 self.scale = float(data[3]) 265 266 return self
267
268 - def keys(self):
269 """returns the list of id define in this blocks""" 270 271 return [p.lhacode for p in self]
272
273 - def __str__(self, precision=''):
274 """ return a str in the SLAH format """ 275 276 text = """###################################""" + \ 277 """\n## INFORMATION FOR %s""" % self.name.upper() +\ 278 """\n###################################\n""" 279 #special case for decay chain 280 if self.name == 'decay': 281 for param in self: 282 pid = param.lhacode[0] 283 param.set_block('decay') 284 text += str(param)+ '\n' 285 if self.decay_table.has_key(pid): 286 text += str(self.decay_table[pid])+'\n' 287 return text 288 elif self.name.startswith('decay'): 289 text = '' # avoid block definition 290 #general case 291 elif not self.scale: 292 text += 'BLOCK %s # %s\n' % (self.name.upper(), self.comment) 293 else: 294 text += 'BLOCK %s Q= %e # %s\n' % (self.name.upper(), self.scale, self.comment) 295 296 text += '\n'.join([param.__str__(precision) for param in self]) 297 return text + '\n'
298
299 300 -class ParamCard(dict):
301 """ a param Card: list of Block """ 302 mp_prefix = 'MP__' 303 304 header = \ 305 """######################################################################\n""" + \ 306 """## PARAM_CARD AUTOMATICALY GENERATED BY MG5 ####\n""" + \ 307 """######################################################################\n""" 308 309
310 - def __init__(self, input_path=None):
311 dict.__init__(self,{}) 312 self.order = [] 313 self.not_parsed_entry = [] 314 315 if isinstance(input_path, ParamCard): 316 self.read(input_path.write()) 317 self.input_path = input_path.input_path 318 else: 319 self.input_path = input_path 320 if input_path: 321 self.read(input_path)
322
323 - def read(self, input_path):
324 """ read a card and full this object with the content of the card """ 325 326 if isinstance(input_path, str): 327 if '\n' in input_path: 328 input = StringIO.StringIO(input_path) 329 else: 330 input = open(input_path) 331 else: 332 input = input_path #Use for banner loading and test 333 334 335 cur_block = None 336 for line in input: 337 line = line.strip() 338 if not line or line[0] == '#': 339 continue 340 line = line.lower() 341 if line.startswith('block'): 342 cur_block = Block() 343 cur_block.load_str(line) 344 self.append(cur_block) 345 continue 346 347 if line.startswith('decay'): 348 if not self.has_block('decay'): 349 cur_block = Block('decay') 350 self.append(cur_block) 351 else: 352 cur_block = self['decay'] 353 param = Parameter() 354 param.set_block(cur_block.name) 355 param.load_str(line[6:]) 356 cur_block.append(param) 357 continue 358 359 if line.startswith('xsection') or cur_block == 'notparsed': 360 cur_block = 'notparsed' 361 self.not_parsed_entry.append(line) 362 continue 363 364 365 if cur_block is None: 366 continue 367 368 if cur_block.name == 'decay': 369 # This is a decay table 370 id = cur_block[-1].lhacode[0] 371 cur_block = Block('decay_table_%s' % id) 372 self['decay'].decay_table[id] = cur_block 373 374 if cur_block.name.startswith('decay_table'): 375 param = Parameter() 376 param.load_decay(line) 377 try: 378 cur_block.append(param) 379 except InvalidParamCard: 380 pass 381 else: 382 param = Parameter() 383 param.set_block(cur_block.name) 384 param.load_str(line) 385 cur_block.append(param) 386 387 return self
388
389 - def __setitem__(self, name, value):
390 391 return dict.__setitem__(self, name.lower(), value)
392
393 - def __getitem__(self, name):
394 return dict.__getitem__(self,name.lower())
395
396 - def analyze_param_card(self):
397 """ Analyzes the comment of the parameter in the param_card and returns 398 a dictionary with parameter names in values and the tuple (lhablock, id) 399 in value as well as a dictionary for restricted values. 400 WARNING: THIS FUNCTION RELIES ON THE FORMATTING OF THE COMMENT IN THE 401 CARD TO FETCH THE PARAMETER NAME. This is mostly ok on the *_default.dat 402 but typically dangerous on the user-defined card.""" 403 404 pname2block = {} 405 restricted_value = {} 406 407 for bname, block in self.items(): 408 for lha_id, param in block.param_dict.items(): 409 all_var = [] 410 comment = param.comment 411 # treat merge parameter 412 if comment.strip().startswith('set of param :'): 413 all_var = list(re.findall(r'''[^-]1\*(\w*)\b''', comment)) 414 # just the variable name as comment 415 elif len(comment.split()) == 1: 416 all_var = [comment.strip().lower()] 417 # either contraction or not formatted 418 else: 419 split = comment.split() 420 if len(split) >2 and split[1] == ':': 421 # NO VAR associated 422 restricted_value[(bname, lha_id)] = ' '.join(split[1:]) 423 elif len(split) == 2: 424 if re.search(r'''\[[A-Z]\]eV\^''', split[1]): 425 all_var = [comment.strip().lower()] 426 elif len(split) >=2 and split[1].startswith('('): 427 all_var = [split[0].strip().lower()] 428 else: 429 if not bname.startswith('qnumbers'): 430 logger.debug("not recognize information for %s %s : %s", 431 bname, lha_id, comment) 432 # not recognized format 433 continue 434 435 for var in all_var: 436 var = var.lower() 437 if var in pname2block: 438 pname2block[var].append((bname, lha_id)) 439 else: 440 pname2block[var] = [(bname, lha_id)] 441 442 return pname2block, restricted_value
443
444 - def update_dependent(self, model, restrict_rule, loglevel):
445 """update the parameter of the card which are not free parameter 446 (i.e mass and width) 447 loglevel can be: None 448 info 449 warning 450 crash # raise an error 451 return if the param_card was modified or not 452 """ 453 modify = False 454 if isinstance(restrict_rule, str): 455 restrict_rule = ParamCardRule(restrict_rule) 456 457 # apply all the basic restriction rule 458 if restrict_rule: 459 _, modify = restrict_rule.check_param_card(self, modify=True, log=loglevel) 460 461 import models.model_reader as model_reader 462 import madgraph.core.base_objects as base_objects 463 if not isinstance(model, model_reader.ModelReader): 464 model = model_reader.ModelReader(model) 465 parameters = model.set_parameters_and_couplings(self) 466 else: 467 parameters = model.set_parameters_and_couplings(self) 468 469 470 for particle in model.get('particles'): 471 if particle.get('goldstone') or particle.get('ghost'): 472 continue 473 mass = model.get_parameter(particle.get('mass')) 474 lhacode = abs(particle.get_pdg_code()) 475 476 if isinstance(mass, base_objects.ModelVariable) and not isinstance(mass, base_objects.ParamCardVariable): 477 try: 478 param_value = self.get('mass').get(lhacode).value 479 except Exception: 480 param = Parameter(block='mass', lhacode=(lhacode,),value=0,comment='added') 481 param_value = -999.999 482 self.get('mass').append(param) 483 model_value = parameters[particle.get('mass')] 484 if isinstance(model_value, complex): 485 if model_value.imag > 1e-5 * model_value.real: 486 raise Exception, "Mass should be real number: particle %s (%s) has mass: %s" % (lhacode, particle.get('name'), model_value) 487 model_value = model_value.real 488 489 if not misc.equal(model_value, param_value, 4): 490 modify = True 491 if loglevel == 20: 492 logger.info('For consistency, the mass of particle %s (%s) is changed to %s.' % (lhacode, particle.get('name'), model_value), '$MG:BOLD') 493 else: 494 logger.log(loglevel, 'For consistency, the mass of particle %s (%s) is changed to %s.' % (lhacode, particle.get('name'), model_value)) 495 #logger.debug('was %s', param_value) 496 if model_value != param_value: 497 self.get('mass').get(abs(particle.get_pdg_code())).value = model_value 498 499 width = model.get_parameter(particle.get('width')) 500 if isinstance(width, base_objects.ModelVariable): 501 try: 502 param_value = self.get('decay').get(lhacode).value 503 except Exception: 504 param = Parameter(block='decay', lhacode=(lhacode,),value=0,comment='added') 505 param_value = -999.999 506 self.get('decay').append(param) 507 model_value = parameters[particle.get('width')] 508 if isinstance(model_value, complex): 509 if model_value.imag > 1e-5 * model_value.real: 510 raise Exception, "Width should be real number: particle %s (%s) has mass: %s" 511 model_value = model_value.real 512 if not misc.equal(abs(model_value), param_value, 4): 513 modify = True 514 if loglevel == 20: 515 logger.info('For consistency, the width of particle %s (%s) is changed to %s.' % (lhacode, particle.get('name'), model_value), '$MG:BOLD') 516 else: 517 logger.log(loglevel,'For consistency, the width of particle %s (%s) is changed to %s.' % (lhacode, particle.get('name'), model_value)) 518 #logger.debug('was %s', param_value) 519 if abs(model_value) != param_value: 520 self.get('decay').get(abs(particle.get_pdg_code())).value = abs(model_value) 521 522 return modify
523 524
525 - def write(self, outpath=None, precision=''):
526 """schedular for writing a card""" 527 528 # order the block in a smart way 529 blocks = self.order_block() 530 text = self.header 531 text += ''.join([block.__str__(precision) for block in blocks]) 532 text += '\n' 533 text += '\n'.join(self.not_parsed_entry) 534 if not outpath: 535 return text 536 elif isinstance(outpath, str): 537 file(outpath,'w').write(text) 538 else: 539 outpath.write(text) # for test purpose
540
541 - def create_diff(self, new_card):
542 """return a text file allowing to pass from this card to the new one 543 via the set command""" 544 545 diff = '' 546 for blockname, block in self.items(): 547 for param in block: 548 lhacode = param.lhacode 549 value = param.value 550 new_value = new_card[blockname].get(lhacode).value 551 if not misc.equal(value, new_value, 6, zero_limit=False): 552 lhacode = ' '.join([str(i) for i in lhacode]) 553 diff += 'set param_card %s %s %s # orig: %s\n' % \ 554 (blockname, lhacode , new_value, value) 555 return diff
556 557
558 - def get_value(self, blockname, lhecode, default=None):
559 try: 560 return self[blockname].get(lhecode).value 561 except KeyError: 562 if blockname == 'width': 563 blockname = 'decay' 564 return self.get_value(blockname, lhecode,default=default) 565 elif default is not None: 566 return default 567 raise
568
569 - def get_missing_block(self, identpath):
570 """ """ 571 missing = set() 572 all_blocks = set(self.keys()) 573 for line in open(identpath): 574 if line.startswith('c ') or line.startswith('ccccc'): 575 continue 576 split = line.split() 577 if len(split) < 3: 578 continue 579 block = split[0] 580 if block not in self: 581 missing.add(block) 582 elif block in all_blocks: 583 all_blocks.remove(block) 584 585 unknow = all_blocks 586 return missing, unknow
587
588 - def secure_slha2(self,identpath):
589 590 missing_set, unknow_set = self.get_missing_block(identpath) 591 592 apply_conversion = [] 593 if missing_set == set(['fralpha']) and 'alpha' in unknow_set: 594 apply_conversion.append('alpha') 595 elif all([b in missing_set for b in ['te','msl2','dsqmix','tu','selmix','msu2','msq2','usqmix','td', 'mse2','msd2']]) and\ 596 all(b in unknow_set for b in ['ae','ad','sbotmix','au','modsel','staumix','stopmix']): 597 apply_conversion.append('to_slha2') 598 599 if 'to_slha2' in apply_conversion: 600 logger.error('Convention for the param_card seems to be wrong. Trying to automatically convert your file to SLHA2 format. \n'+\ 601 "Please check that the conversion occurs as expected (The converter is not fully general)") 602 603 param_card =self.input_path 604 convert_to_mg5card(param_card, writting=True) 605 self.clear() 606 self.__init__(param_card) 607 608 if 'alpha' in apply_conversion: 609 logger.info("Missing block fralpha but found a block alpha, apply automatic conversion") 610 self.rename_blocks({'alpha':'fralpha'}) 611 self['fralpha'].rename_keys({(): (1,)}) 612 self.write(param_card.input_path)
613
614 - def write_inc_file(self, outpath, identpath, default, need_mp=False):
615 """ write a fortran file which hardcode the param value""" 616 617 self.secure_slha2(identpath) 618 619 620 fout = file_writers.FortranWriter(outpath) 621 defaultcard = ParamCard(default) 622 for line in open(identpath): 623 if line.startswith('c ') or line.startswith('ccccc'): 624 continue 625 split = line.split() 626 if len(split) < 3: 627 continue 628 block = split[0] 629 lhaid = [int(i) for i in split[1:-1]] 630 variable = split[-1] 631 if block in self: 632 try: 633 value = self[block].get(tuple(lhaid)).value 634 except KeyError: 635 value =defaultcard[block].get(tuple(lhaid)).value 636 logger.warning('information about \"%s %s" is missing using default value: %s.' %\ 637 (block, lhaid, value)) 638 else: 639 value =defaultcard[block].get(tuple(lhaid)).value 640 logger.warning('information about \"%s %s" is missing (full block missing) using default value: %s.' %\ 641 (block, lhaid, value)) 642 value = str(value).lower() 643 #special handling for negative mass -> set width negative 644 if block == 'decay': 645 if self['mass'].get(tuple(lhaid)).value < 0: 646 value = '-%s' % value 647 648 fout.writelines(' %s = %s' % (variable, ('%e'%float(value)).replace('e','d'))) 649 if need_mp: 650 fout.writelines(' mp__%s = %s_16' % (variable, value))
651
653 """ Convert this param_card to the convention used for the complex mass scheme: 654 This includes, removing the Yukawa block if present and making sure the EW input 655 scheme is (MZ, MW, aewm1). """ 656 657 # The yukawa block is irrelevant for the CMS models, we must remove them 658 if self.has_block('yukawa'): 659 # Notice that the last parameter removed will also remove the block. 660 for lhacode in [param.lhacode for param in self['yukawa']]: 661 self.remove_param('yukawa', lhacode) 662 663 # Now fix the EW input scheme 664 EW_input = {('sminputs',(1,)):None, 665 ('sminputs',(2,)):None, 666 ('mass',(23,)):None, 667 ('mass',(24,)):None} 668 for block, lhaid in EW_input.keys(): 669 try: 670 EW_input[(block,lhaid)] = self[block].get(lhaid).value 671 except: 672 pass 673 674 # Now specify the missing values. We only support the following EW 675 # input scheme: 676 # (alpha, GF, MZ) input 677 internal_param = [key for key,value in EW_input.items() if value is None] 678 if len(internal_param)==0: 679 # All parameters are already set, no need for modifications 680 return 681 682 if len(internal_param)!=1: 683 raise InvalidParamCard,' The specified EW inputs has more than one'+\ 684 ' unknown: [%s]'%(','.join([str(elem) for elem in internal_param])) 685 686 687 if not internal_param[0] in [('mass',(24,)), ('sminputs',(2,)), 688 ('sminputs',(1,))]: 689 raise InvalidParamCard, ' The only EW input scheme currently supported'+\ 690 ' are those with either the W mass or GF left internal.' 691 692 # Now if the Wmass is internal, then we must change the scheme 693 if internal_param[0] == ('mass',(24,)): 694 aewm1 = EW_input[('sminputs',(1,))] 695 Gf = EW_input[('sminputs',(2,))] 696 Mz = EW_input[('mass',(23,))] 697 try: 698 Mw = math.sqrt((Mz**2/2.0)+math.sqrt((Mz**4/4.0)-(( 699 (1.0/aewm1)*math.pi*Mz**2)/(Gf*math.sqrt(2.0))))) 700 except: 701 InvalidParamCard, 'The EW inputs 1/a_ew=%f, Gf=%f, Mz=%f are inconsistent'%\ 702 (aewm1,Gf,Mz) 703 self.remove_param('sminputs', (2,)) 704 self.add_param('mass', (24,), Mw, 'MW')
705
706 - def append(self, obj):
707 """add an object to this""" 708 709 assert isinstance(obj, Block) 710 self[obj.name] = obj 711 if not obj.name.startswith('decay_table'): 712 self.order.append(obj)
713 714 715
716 - def has_block(self, name):
717 return self.has_key(name)
718
719 - def order_block(self):
720 """ reorganize the block """ 721 return self.order
722
723 - def rename_blocks(self, name_dict):
724 """ rename the blocks """ 725 726 for old_name, new_name in name_dict.items(): 727 self[new_name] = self.pop(old_name) 728 self[new_name].name = new_name 729 for param in self[new_name]: 730 param.lhablock = new_name
731
732 - def remove_block(self, name):
733 """ remove a blocks """ 734 assert len(self[name])==0 735 [self.order.pop(i) for i,b in enumerate(self.order) if b.name == name] 736 self.pop(name)
737
738 - def remove_param(self, block, lhacode):
739 """ remove a parameter """ 740 if self.has_param(block, lhacode): 741 self[block].remove(lhacode) 742 if len(self[block]) == 0: 743 self.remove_block(block)
744
745 - def has_param(self, block, lhacode):
746 """check if param exists""" 747 748 try: 749 self[block].get(lhacode) 750 except: 751 return False 752 else: 753 return True
754
755 - def copy_param(self,old_block, old_lha, block=None, lhacode=None):
756 """ make a parameter, a symbolic link on another one """ 757 758 # Find the current block/parameter 759 old_block_obj = self[old_block] 760 parameter = old_block_obj.get(old_lha) 761 if not block: 762 block = old_block 763 if not lhacode: 764 lhacode = old_lha 765 766 self.add_param(block, lhacode, parameter.value, parameter.comment)
767
768 - def add_param(self,block, lha, value, comment=''):
769 770 parameter = Parameter(block=block, lhacode=lha, value=value, 771 comment=comment) 772 try: 773 new_block = self[block] 774 except KeyError: 775 # If the new block didn't exist yet 776 new_block = Block(block) 777 self.append(new_block) 778 new_block.append(parameter)
779
780 - def do_help(self, block, lhacode, default=None):
781 782 if not lhacode: 783 logger.info("Information on block parameter %s:" % block, '$MG:color:BLUE') 784 print str(self[block]) 785 elif default: 786 pname2block, restricted = default.analyze_param_card() 787 if (block, lhacode) in restricted: 788 logger.warning("This parameter will not be consider by MG5_aMC") 789 print( " MadGraph will use the following formula:") 790 print restricted[(block, lhacode)] 791 print( " Note that some code (MadSpin/Pythia/...) will read directly the value") 792 else: 793 for name, values in pname2block.items(): 794 if (block, lhacode) in values: 795 valid_name = name 796 break 797 logger.info("Information for parameter %s of the param_card" % valid_name, '$MG:color:BLUE') 798 print("Part of Block \"%s\" with identification number %s" % (block, lhacode)) 799 print("Current value: %s" % self[block].get(lhacode).value) 800 print("Default value: %s" % default[block].get(lhacode).value) 801 print("comment present in the cards: %s " % default[block].get(lhacode).comment)
802 803 804 805
806 - def mod_param(self, old_block, old_lha, block=None, lhacode=None, 807 value=None, comment=None):
808 """ change a parameter to a new one. This is not a duplication.""" 809 810 # Find the current block/parameter 811 old_block = self[old_block] 812 try: 813 parameter = old_block.get(old_lha) 814 except: 815 if lhacode is not None: 816 lhacode=old_lha 817 self.add_param(block, lhacode, value, comment) 818 return 819 820 821 # Update the parameter 822 if block: 823 parameter.lhablock = block 824 if lhacode: 825 parameter.lhacode = lhacode 826 if value: 827 parameter.value = value 828 if comment: 829 parameter.comment = comment 830 831 # Change the block of the parameter 832 if block: 833 old_block.remove(old_lha) 834 if not len(old_block): 835 self.remove_block(old_block.name) 836 try: 837 new_block = self[block] 838 except KeyError: 839 # If the new block didn't exist yet 840 new_block = Block(block) 841 self.append(new_block) 842 new_block.append(parameter) 843 elif lhacode: 844 old_block.param_dict[tuple(lhacode)] = \ 845 old_block.param_dict.pop(tuple(old_lha))
846 847
848 - def check_and_remove(self, block, lhacode, value):
849 """ check that the value is coherent and remove it""" 850 851 if self.has_param(block, lhacode): 852 param = self[block].get(lhacode) 853 if param.value != value: 854 error_msg = 'This card is not suitable to be convert to SLAH1\n' 855 error_msg += 'Parameter %s %s should be %s' % (block, lhacode, value) 856 raise InvalidParamCard, error_msg 857 self.remove_param(block, lhacode)
858
859 860 -class ParamCardMP(ParamCard):
861 """ a param Card: list of Block with also MP definition of variables""" 862
863 - def write_inc_file(self, outpath, identpath, default):
864 """ write a fortran file which hardcode the param value""" 865 866 fout = file_writers.FortranWriter(outpath) 867 defaultcard = ParamCard(default) 868 for line in open(identpath): 869 if line.startswith('c ') or line.startswith('ccccc'): 870 continue 871 split = line.split() 872 if len(split) < 3: 873 continue 874 block = split[0] 875 lhaid = [int(i) for i in split[1:-1]] 876 variable = split[-1] 877 if block in self: 878 try: 879 value = self[block].get(tuple(lhaid)).value 880 except KeyError: 881 value =defaultcard[block].get(tuple(lhaid)).value 882 else: 883 value =defaultcard[block].get(tuple(lhaid)).value 884 #value = str(value).lower() 885 fout.writelines(' %s = %s' % (variable, ('%e' % value).replace('e','d'))) 886 fout.writelines(' %s%s = %s_16' % (self.mp_prefix, 887 variable, ('%e' % value)))
888
889 890 891 892 -class ParamCardIterator(ParamCard):
893 """A class keeping track of the scan: flag in the param_card and 894 having an __iter__() function to scan over all the points of the scan. 895 """ 896 897 logging = True
898 - def __init__(self, input_path=None):
899 super(ParamCardIterator, self).__init__(input_path=input_path) 900 self.itertag = [] #all the current value use 901 self.cross = [] # keep track of all the cross-section computed 902 self.param_order = []
903
904 - def __iter__(self):
905 """generate the next param_card (in a abstract way) related to the scan. 906 Technically this generates only the generator.""" 907 908 if hasattr(self, 'iterator'): 909 return self.iterator 910 self.iterator = self.iterate() 911 return self.iterator
912
913 - def next(self, autostart=False):
914 """call the next iteration value""" 915 try: 916 iterator = self.iterator 917 except: 918 if autostart: 919 iterator = self.__iter__() 920 else: 921 raise 922 try: 923 out = iterator.next() 924 except StopIteration: 925 del self.iterator 926 raise 927 return out
928
929 - def iterate(self):
930 """create the actual generator""" 931 all_iterators = {} # dictionary of key -> block of object to scan [([param, [values]), ...] 932 pattern = re.compile(r'''scan\s*(?P<id>\d*)\s*:\s*(?P<value>[^#]*)''', re.I) 933 self.autowidth = [] 934 # First determine which parameter to change and in which group 935 # so far only explicit value of the scan (no lambda function are allowed) 936 for block in self.order: 937 for param in block: 938 if isinstance(param.value, str) and param.value.strip().lower().startswith('scan'): 939 try: 940 key, def_list = pattern.findall(param.value)[0] 941 except: 942 raise Exception, "Fail to handle scanning tag: Please check that the syntax is valid" 943 if key == '': 944 key = -1 * len(all_iterators) 945 if key not in all_iterators: 946 all_iterators[key] = [] 947 try: 948 all_iterators[key].append( (param, eval(def_list))) 949 except SyntaxError, error: 950 raise Exception, "Fail to handle your scan definition. Please check your syntax:\n entry: %s \n Error reported: %s" %(def_list, error) 951 elif isinstance(param.value, str) and param.value.strip().lower().startswith('auto'): 952 self.autowidth.append(param) 953 keys = all_iterators.keys() # need to fix an order for the scan 954 param_card = ParamCard(self) 955 #store the type of parameter 956 for key in keys: 957 for param, values in all_iterators[key]: 958 self.param_order.append("%s#%s" % (param.lhablock, '_'.join(`i` for i in param.lhacode))) 959 960 # do the loop 961 lengths = [range(len(all_iterators[key][0][1])) for key in keys] 962 for positions in itertools.product(*lengths): 963 self.itertag = [] 964 if self.logging: 965 logger.info("Create the next param_card in the scan definition", '$MG:BOLD') 966 for i, pos in enumerate(positions): 967 key = keys[i] 968 for param, values in all_iterators[key]: 969 # assign the value in the card. 970 param_card[param.lhablock].get(param.lhacode).value = values[pos] 971 self.itertag.append(values[pos]) 972 if self.logging: 973 logger.info("change parameter %s with code %s to %s", \ 974 param.lhablock, param.lhacode, values[pos]) 975 976 977 # retrun the current param_card up to next iteration 978 yield param_card
979 980
981 - def store_entry(self, run_name, cross, error=None, param_card_path=None):
982 """store the value of the cross-section""" 983 984 if isinstance(cross, dict): 985 info = dict(cross) 986 info.update({'bench' : self.itertag, 'run_name': run_name}) 987 self.cross.append(info) 988 else: 989 if error is None: 990 self.cross.append({'bench' : self.itertag, 'run_name': run_name, 'cross(pb)':cross}) 991 else: 992 self.cross.append({'bench' : self.itertag, 'run_name': run_name, 'cross(pb)':cross, 'error(pb)':error}) 993 994 if self.autowidth and param_card_path: 995 paramcard = ParamCard(param_card_path) 996 for param in self.autowidth: 997 self.cross[-1]['width#%s' % param.lhacode[0]] = paramcard.get_value(param.lhablock, param.lhacode)
998 999
1000 - def write_summary(self, path, order=None, lastline=False, nbcol=20):
1001 """ """ 1002 1003 if path: 1004 ff = open(path, 'w') 1005 else: 1006 ff = StringIO.StringIO() 1007 if order: 1008 keys = order 1009 else: 1010 keys = self.cross[0].keys() 1011 if 'bench' in keys: keys.remove('bench') 1012 if 'run_name' in keys: keys.remove('run_name') 1013 keys.sort() 1014 if 'cross(pb)' in keys: 1015 keys.remove('cross(pb)') 1016 keys.append('cross(pb)') 1017 if 'error(pb)' in keys: 1018 keys.remove('error(pb)') 1019 keys.append('error(pb)') 1020 1021 formatting = "#%s%s%s\n" %('%%-%is ' % (nbcol-1), ('%%-%is ' % (nbcol))* len(self.param_order), 1022 ('%%-%is ' % (nbcol))* len(keys)) 1023 # header 1024 if not lastline: 1025 ff.write(formatting % tuple(['run_name'] + self.param_order + keys)) 1026 formatting = "%s%s%s\n" %('%%-%is ' % (nbcol), ('%%-%ie ' % (nbcol))* len(self.param_order), 1027 ('%%-%ie ' % (nbcol))* len(keys)) 1028 1029 1030 if not lastline: 1031 to_print = self.cross 1032 else: 1033 to_print = self.cross[-1:] 1034 1035 for info in to_print: 1036 name = info['run_name'] 1037 bench = info['bench'] 1038 data = [] 1039 for k in keys: 1040 if k in info: 1041 data.append(info[k]) 1042 else: 1043 data.append(0.) 1044 ff.write(formatting % tuple([name] + bench + data)) 1045 1046 if not path: 1047 return ff.getvalue()
1048 1049
1050 - def get_next_name(self, run_name):
1051 """returns a smart name for the next run""" 1052 1053 if '_' in run_name: 1054 name, value = run_name.rsplit('_',1) 1055 if value.isdigit(): 1056 return '%s_%02i' % (name, float(value)+1) 1057 # no valid '_' in the name 1058 return '%s_scan_02' % run_name
1059
1060 1061 1062 -class ParamCardRule(object):
1063 """ A class for storing the linked between the different parameter of 1064 the param_card. 1065 Able to write a file 'param_card_rule.dat' 1066 Able to read a file 'param_card_rule.dat' 1067 Able to check the validity of a param_card.dat 1068 """ 1069 1070
1071 - def __init__(self, inputpath=None):
1072 """initialize an object """ 1073 1074 # constraint due to model restriction 1075 self.zero = [] 1076 self.one = [] 1077 self.identical = [] 1078 self.opposite = [] 1079 1080 # constraint due to the model 1081 self.rule = [] 1082 1083 if inputpath: 1084 self.load_rule(inputpath)
1085
1086 - def add_zero(self, lhablock, lhacode, comment=''):
1087 """add a zero rule""" 1088 self.zero.append( (lhablock, lhacode, comment) )
1089
1090 - def add_one(self, lhablock, lhacode, comment=''):
1091 """add a one rule""" 1092 self.one.append( (lhablock, lhacode, comment) )
1093
1094 - def add_identical(self, lhablock, lhacode, lhacode2, comment=''):
1095 """add a rule for identical value""" 1096 self.identical.append( (lhablock, lhacode, lhacode2, comment) )
1097
1098 - def add_opposite(self, lhablock, lhacode, lhacode2, comment=''):
1099 """add a rule for identical value""" 1100 self.opposite.append( (lhablock, lhacode, lhacode2, comment) )
1101 1102
1103 - def add_rule(self, lhablock, lhacode, rule, comment=''):
1104 """add a rule for constraint value""" 1105 self.rule.append( (lhablock, lhacode, rule) )
1106
1107 - def write_file(self, output=None):
1108 1109 text = """<file>###################################################################### 1110 ## VALIDITY RULE FOR THE PARAM_CARD #### 1111 ######################################################################\n""" 1112 1113 # ZERO 1114 text +='<zero>\n' 1115 for name, id, comment in self.zero: 1116 text+=' %s %s # %s\n' % (name, ' '.join([str(i) for i in id]), 1117 comment) 1118 # ONE 1119 text +='</zero>\n<one>\n' 1120 for name, id, comment in self.one: 1121 text+=' %s %s # %s\n' % (name, ' '.join([str(i) for i in id]), 1122 comment) 1123 # IDENTICAL 1124 text +='</one>\n<identical>\n' 1125 for name, id,id2, comment in self.identical: 1126 text+=' %s %s : %s # %s\n' % (name, ' '.join([str(i) for i in id]), 1127 ' '.join([str(i) for i in id2]), comment) 1128 1129 # OPPOSITE 1130 text +='</identical>\n<opposite>\n' 1131 for name, id,id2, comment in self.opposite: 1132 text+=' %s %s : %s # %s\n' % (name, ' '.join([str(i) for i in id]), 1133 ' '.join([str(i) for i in id2]), comment) 1134 1135 # CONSTRAINT 1136 text += '</opposite>\n<constraint>\n' 1137 for name, id, rule, comment in self.rule: 1138 text += ' %s %s : %s # %s\n' % (name, ' '.join([str(i) for i in id]), 1139 rule, comment) 1140 text += '</constraint>\n</file>' 1141 1142 if isinstance(output, str): 1143 output = open(output,'w') 1144 if hasattr(output, 'write'): 1145 output.write(text) 1146 return text
1147
1148 - def load_rule(self, inputpath):
1149 """ import a validity rule file """ 1150 1151 1152 try: 1153 tree = ET.parse(inputpath) 1154 except IOError: 1155 if '\n' in inputpath: 1156 # this is convinient for the tests 1157 tree = ET.fromstring(inputpath) 1158 else: 1159 raise 1160 1161 #Add zero element 1162 element = tree.find('zero') 1163 if element is not None: 1164 for line in element.text.split('\n'): 1165 line = line.split('#',1)[0] 1166 if not line: 1167 continue 1168 lhacode = line.split() 1169 blockname = lhacode.pop(0) 1170 lhacode = [int(code) for code in lhacode ] 1171 self.add_zero(blockname, lhacode, '') 1172 1173 #Add one element 1174 element = tree.find('one') 1175 if element is not None: 1176 for line in element.text.split('\n'): 1177 line = line.split('#',1)[0] 1178 if not line: 1179 continue 1180 lhacode = line.split() 1181 blockname = lhacode.pop(0) 1182 lhacode = [int(code) for code in lhacode ] 1183 self.add_one(blockname, lhacode, '') 1184 1185 #Add Identical element 1186 element = tree.find('identical') 1187 if element is not None: 1188 for line in element.text.split('\n'): 1189 line = line.split('#',1)[0] 1190 if not line: 1191 continue 1192 line, lhacode2 = line.split(':') 1193 lhacode = line.split() 1194 blockname = lhacode.pop(0) 1195 lhacode = [int(code) for code in lhacode ] 1196 lhacode2 = [int(code) for code in lhacode2.split() ] 1197 self.add_identical(blockname, lhacode, lhacode2, '') 1198 1199 #Add Opposite element 1200 element = tree.find('opposite') 1201 if element is not None: 1202 for line in element.text.split('\n'): 1203 line = line.split('#',1)[0] 1204 if not line: 1205 continue 1206 line, lhacode2 = line.split(':') 1207 lhacode = line.split() 1208 blockname = lhacode.pop(0) 1209 lhacode = [int(code) for code in lhacode ] 1210 lhacode2 = [int(code) for code in lhacode2.split() ] 1211 self.add_opposite(blockname, lhacode, lhacode2, '') 1212 1213 #Add Rule element 1214 element = tree.find('rule') 1215 if element is not None: 1216 for line in element.text.split('\n'): 1217 line = line.split('#',1)[0] 1218 if not line: 1219 continue 1220 line, rule = line.split(':') 1221 lhacode = line.split() 1222 blockname = lhacode.pop(0) 1223 self.add_rule(blockname, lhacode, rule, '')
1224 1225 @staticmethod
1226 - def read_param_card(path):
1227 """ read a param_card and return a dictionary with the associated value.""" 1228 1229 output = ParamCard(path) 1230 1231 1232 1233 return output
1234 1235 @staticmethod
1236 - def write_param_card(path, data):
1237 """ read a param_card and return a dictionary with the associated value.""" 1238 1239 output = {} 1240 1241 if isinstance(path, str): 1242 output = open(path, 'w') 1243 else: 1244 output = path # helpfull for the test 1245 1246 data.write(path)
1247 1248
1249 - def check_param_card(self, path, modify=False, write_missing=False, log=False):
1250 """Check that the restriction card are applied""" 1251 1252 is_modified = False 1253 1254 if isinstance(path,str): 1255 card = self.read_param_card(path) 1256 else: 1257 card = path 1258 1259 # check zero 1260 for block, id, comment in self.zero: 1261 try: 1262 value = float(card[block].get(id).value) 1263 except KeyError: 1264 if modify and write_missing: 1265 new_param = Parameter(block=block,lhacode=id, value=0, 1266 comment='fixed by the model') 1267 if block in card: 1268 card[block].append(new_param) 1269 else: 1270 new_block = Block(block) 1271 card.append(new_block) 1272 new_block.append(new_param) 1273 else: 1274 if value != 0: 1275 if not modify: 1276 raise InvalidParamCard, 'parameter %s: %s is not at zero' % \ 1277 (block, ' '.join([str(i) for i in id])) 1278 else: 1279 param = card[block].get(id) 1280 param.value = 0.0 1281 param.comment += ' fixed by the model' 1282 is_modified = True 1283 if log ==20: 1284 logger.log(log,'For model consistency, update %s with id %s to value %s', 1285 block, id, 0.0, '$MG:BOLD') 1286 elif log: 1287 logger.log(log,'For model consistency, update %s with id %s to value %s', 1288 block, id, 0.0) 1289 1290 # check one 1291 for block, id, comment in self.one: 1292 try: 1293 value = card[block].get(id).value 1294 except KeyError: 1295 if modify and write_missing: 1296 new_param = Parameter(block=block,lhacode=id, value=1, 1297 comment='fixed by the model') 1298 if block in card: 1299 card[block].append(new_param) 1300 else: 1301 new_block = Block(block) 1302 card.append(new_block) 1303 new_block.append(new_param) 1304 else: 1305 if value != 1: 1306 if not modify: 1307 raise InvalidParamCard, 'parameter %s: %s is not at one but at %s' % \ 1308 (block, ' '.join([str(i) for i in id]), value) 1309 else: 1310 param = card[block].get(id) 1311 param.value = 1.0 1312 param.comment += ' fixed by the model' 1313 is_modified = True 1314 if log ==20: 1315 logger.log(log,'For model consistency, update %s with id %s to value %s', 1316 (block, id, 1.0), '$MG:BOLD') 1317 elif log: 1318 logger.log(log,'For model consistency, update %s with id %s to value %s', 1319 (block, id, 1.0)) 1320 1321 1322 # check identical 1323 for block, id1, id2, comment in self.identical: 1324 if block not in card: 1325 is_modified = True 1326 logger.warning('''Param card is not complete: Block %s is simply missing. 1327 We will use model default for all missing value! Please cross-check that 1328 this correspond to your expectation.''' % block) 1329 continue 1330 value2 = float(card[block].get(id2).value) 1331 try: 1332 param = card[block].get(id1) 1333 except KeyError: 1334 if modify and write_missing: 1335 new_param = Parameter(block=block,lhacode=id1, value=value2, 1336 comment='must be identical to %s' %id2) 1337 card[block].append(new_param) 1338 else: 1339 value1 = float(param.value) 1340 1341 if value1 != value2: 1342 if not modify: 1343 raise InvalidParamCard, 'parameter %s: %s is not to identical to parameter %s' % \ 1344 (block, ' '.join([str(i) for i in id1]), 1345 ' '.join([str(i) for i in id2])) 1346 else: 1347 param = card[block].get(id1) 1348 param.value = value2 1349 param.comment += ' must be identical to %s' % id2 1350 is_modified = True 1351 if log ==20: 1352 logger.log(log,'For model consistency, update %s with id %s to value %s since it should be equal to parameter with id %s', 1353 block, id1, value2, id2, '$MG:BOLD') 1354 elif log: 1355 logger.log(log,'For model consistency, update %s with id %s to value %s since it should be equal to parameter with id %s', 1356 block, id1, value2, id2) 1357 # check opposite 1358 for block, id1, id2, comment in self.opposite: 1359 value2 = float(card[block].get(id2).value) 1360 try: 1361 param = card[block].get(id1) 1362 except KeyError: 1363 if modify and write_missing: 1364 new_param = Parameter(block=block,lhacode=id1, value=-value2, 1365 comment='must be opposite to to %s' %id2) 1366 card[block].append(new_param) 1367 else: 1368 value1 = float(param.value) 1369 1370 if value1 != -value2: 1371 if not modify: 1372 raise InvalidParamCard, 'parameter %s: %s is not to opposite to parameter %s' % \ 1373 (block, ' '.join([str(i) for i in id1]), 1374 ' '.join([str(i) for i in id2])) 1375 else: 1376 param = card[block].get(id1) 1377 param.value = -value2 1378 param.comment += ' must be opposite to %s' % id2 1379 is_modified = True 1380 if log ==20: 1381 logger.log(log,'For model consistency, update %s with id %s to value %s since it should be equal to the opposite of the parameter with id %s', 1382 block, id1, -value2, id2, '$MG:BOLD') 1383 elif log: 1384 logger.log(log,'For model consistency, update %s with id %s to value %s since it should be equal to the opposite of the parameter with id %s', 1385 block, id1, -value2, id2) 1386 1387 return card, is_modified
1388
1389 1390 -def convert_to_slha1(path, outputpath=None ):
1391 """ """ 1392 1393 if not outputpath: 1394 outputpath = path 1395 card = ParamCard(path) 1396 if not 'usqmix' in card: 1397 #already slha1 1398 card.write(outputpath) 1399 return 1400 1401 # Mass 1402 #card.reorder_mass() # needed? 1403 card.copy_param('mass', [6], 'sminputs', [6]) 1404 card.copy_param('mass', [15], 'sminputs', [7]) 1405 card.copy_param('mass', [23], 'sminputs', [4]) 1406 # Decay: Nothing to do. 1407 1408 # MODSEL 1409 card.add_param('modsel',[1], value=1) 1410 card['modsel'].get([1]).format = 'int' 1411 1412 # find scale 1413 scale = card['hmix'].scale 1414 if not scale: 1415 scale = 1 # Need to be define (this is dummy value) 1416 1417 # SMINPUTS 1418 if not card.has_param('sminputs', [2]): 1419 aem1 = card['sminputs'].get([1]).value 1420 mz = card['mass'].get([23]).value 1421 mw = card['mass'].get([24]).value 1422 gf = math.pi / math.sqrt(2) / aem1 * mz**2/ mw**2 /(mz**2-mw**2) 1423 card.add_param('sminputs', [2], gf, 'G_F [GeV^-2]') 1424 1425 # USQMIX 1426 card.check_and_remove('usqmix', [1,1], 1.0) 1427 card.check_and_remove('usqmix', [2,2], 1.0) 1428 card.check_and_remove('usqmix', [4,4], 1.0) 1429 card.check_and_remove('usqmix', [5,5], 1.0) 1430 card.mod_param('usqmix', [3,3], 'stopmix', [1,1]) 1431 card.mod_param('usqmix', [3,6], 'stopmix', [1,2]) 1432 card.mod_param('usqmix', [6,3], 'stopmix', [2,1]) 1433 card.mod_param('usqmix', [6,6], 'stopmix', [2,2]) 1434 1435 # DSQMIX 1436 card.check_and_remove('dsqmix', [1,1], 1.0) 1437 card.check_and_remove('dsqmix', [2,2], 1.0) 1438 card.check_and_remove('dsqmix', [4,4], 1.0) 1439 card.check_and_remove('dsqmix', [5,5], 1.0) 1440 card.mod_param('dsqmix', [3,3], 'sbotmix', [1,1]) 1441 card.mod_param('dsqmix', [3,6], 'sbotmix', [1,2]) 1442 card.mod_param('dsqmix', [6,3], 'sbotmix', [2,1]) 1443 card.mod_param('dsqmix', [6,6], 'sbotmix', [2,2]) 1444 1445 1446 # SELMIX 1447 card.check_and_remove('selmix', [1,1], 1.0) 1448 card.check_and_remove('selmix', [2,2], 1.0) 1449 card.check_and_remove('selmix', [4,4], 1.0) 1450 card.check_and_remove('selmix', [5,5], 1.0) 1451 card.mod_param('selmix', [3,3], 'staumix', [1,1]) 1452 card.mod_param('selmix', [3,6], 'staumix', [1,2]) 1453 card.mod_param('selmix', [6,3], 'staumix', [2,1]) 1454 card.mod_param('selmix', [6,6], 'staumix', [2,2]) 1455 1456 # FRALPHA 1457 card.mod_param('fralpha', [1], 'alpha', [' ']) 1458 1459 #HMIX 1460 if not card.has_param('hmix', [3]): 1461 aem1 = card['sminputs'].get([1]).value 1462 tanb = card['hmix'].get([2]).value 1463 mz = card['mass'].get([23]).value 1464 mw = card['mass'].get([24]).value 1465 sw = math.sqrt(mz**2 - mw**2)/mz 1466 ee = 2 * math.sqrt(1/aem1) * math.sqrt(math.pi) 1467 vu = 2 * mw *sw /ee * math.sin(math.atan(tanb)) 1468 card.add_param('hmix', [3], vu, 'higgs vev(Q) MSSM DRb') 1469 card['hmix'].scale= scale 1470 1471 # VCKM 1472 card.check_and_remove('vckm', [1,1], 1.0) 1473 card.check_and_remove('vckm', [2,2], 1.0) 1474 card.check_and_remove('vckm', [3,3], 1.0) 1475 1476 #SNUMIX 1477 card.check_and_remove('snumix', [1,1], 1.0) 1478 card.check_and_remove('snumix', [2,2], 1.0) 1479 card.check_and_remove('snumix', [3,3], 1.0) 1480 1481 #UPMNS 1482 card.check_and_remove('upmns', [1,1], 1.0) 1483 card.check_and_remove('upmns', [2,2], 1.0) 1484 card.check_and_remove('upmns', [3,3], 1.0) 1485 1486 # Te 1487 ye = card['ye'].get([3, 3]).value 1488 te = card['te'].get([3, 3]).value 1489 card.mod_param('te', [3,3], 'ae', [3,3], value= te/ye, comment='A_tau(Q) DRbar') 1490 card.add_param('ae', [1,1], 0, 'A_e(Q) DRbar') 1491 card.add_param('ae', [2,2], 0, 'A_mu(Q) DRbar') 1492 card['ae'].scale = scale 1493 card['ye'].scale = scale 1494 1495 # Tu 1496 yu = card['yu'].get([3, 3]).value 1497 tu = card['tu'].get([3, 3]).value 1498 card.mod_param('tu', [3,3], 'au', [3,3], value= tu/yu, comment='A_t(Q) DRbar') 1499 card.add_param('au', [1,1], 0, 'A_u(Q) DRbar') 1500 card.add_param('au', [2,2], 0, 'A_c(Q) DRbar') 1501 card['au'].scale = scale 1502 card['yu'].scale = scale 1503 1504 # Td 1505 yd = card['yd'].get([3, 3]).value 1506 td = card['td'].get([3, 3]).value 1507 if td: 1508 card.mod_param('td', [3,3], 'ad', [3,3], value= td/yd, comment='A_b(Q) DRbar') 1509 else: 1510 card.mod_param('td', [3,3], 'ad', [3,3], value= 0., comment='A_b(Q) DRbar') 1511 card.add_param('ad', [1,1], 0, 'A_d(Q) DRbar') 1512 card.add_param('ad', [2,2], 0, 'A_s(Q) DRbar') 1513 card['ad'].scale = scale 1514 card['yd'].scale = scale 1515 1516 # MSL2 1517 value = card['msl2'].get([1, 1]).value 1518 card.mod_param('msl2', [1,1], 'msoft', [31], math.sqrt(value)) 1519 value = card['msl2'].get([2, 2]).value 1520 card.mod_param('msl2', [2,2], 'msoft', [32], math.sqrt(value)) 1521 value = card['msl2'].get([3, 3]).value 1522 card.mod_param('msl2', [3,3], 'msoft', [33], math.sqrt(value)) 1523 card['msoft'].scale = scale 1524 1525 # MSE2 1526 value = card['mse2'].get([1, 1]).value 1527 card.mod_param('mse2', [1,1], 'msoft', [34], math.sqrt(value)) 1528 value = card['mse2'].get([2, 2]).value 1529 card.mod_param('mse2', [2,2], 'msoft', [35], math.sqrt(value)) 1530 value = card['mse2'].get([3, 3]).value 1531 card.mod_param('mse2', [3,3], 'msoft', [36], math.sqrt(value)) 1532 1533 # MSQ2 1534 value = card['msq2'].get([1, 1]).value 1535 card.mod_param('msq2', [1,1], 'msoft', [41], math.sqrt(value)) 1536 value = card['msq2'].get([2, 2]).value 1537 card.mod_param('msq2', [2,2], 'msoft', [42], math.sqrt(value)) 1538 value = card['msq2'].get([3, 3]).value 1539 card.mod_param('msq2', [3,3], 'msoft', [43], math.sqrt(value)) 1540 1541 # MSU2 1542 value = card['msu2'].get([1, 1]).value 1543 card.mod_param('msu2', [1,1], 'msoft', [44], math.sqrt(value)) 1544 value = card['msu2'].get([2, 2]).value 1545 card.mod_param('msu2', [2,2], 'msoft', [45], math.sqrt(value)) 1546 value = card['msu2'].get([3, 3]).value 1547 card.mod_param('msu2', [3,3], 'msoft', [46], math.sqrt(value)) 1548 1549 # MSD2 1550 value = card['msd2'].get([1, 1]).value 1551 card.mod_param('msd2', [1,1], 'msoft', [47], math.sqrt(value)) 1552 value = card['msd2'].get([2, 2]).value 1553 card.mod_param('msd2', [2,2], 'msoft', [48], math.sqrt(value)) 1554 value = card['msd2'].get([3, 3]).value 1555 card.mod_param('msd2', [3,3], 'msoft', [49], math.sqrt(value)) 1556 1557 1558 1559 ################# 1560 # WRITE OUTPUT 1561 ################# 1562 card.write(outputpath)
1563
1564 1565 1566 -def convert_to_mg5card(path, outputpath=None, writting=True):
1567 """ 1568 """ 1569 1570 if not outputpath: 1571 outputpath = path 1572 card = ParamCard(path) 1573 if 'usqmix' in card: 1574 #already mg5(slha2) format 1575 if outputpath != path and writting: 1576 card.write(outputpath) 1577 return card 1578 1579 1580 # SMINPUTS 1581 card.remove_param('sminputs', [2]) 1582 card.remove_param('sminputs', [4]) 1583 card.remove_param('sminputs', [6]) 1584 card.remove_param('sminputs', [7]) 1585 # Decay: Nothing to do. 1586 1587 # MODSEL 1588 card.remove_param('modsel',[1]) 1589 1590 1591 # USQMIX 1592 card.add_param('usqmix', [1,1], 1.0) 1593 card.add_param('usqmix', [2,2], 1.0) 1594 card.add_param('usqmix', [4,4], 1.0) 1595 card.add_param('usqmix', [5,5], 1.0) 1596 card.mod_param('stopmix', [1,1], 'usqmix', [3,3]) 1597 card.mod_param('stopmix', [1,2], 'usqmix', [3,6]) 1598 card.mod_param('stopmix', [2,1], 'usqmix', [6,3]) 1599 card.mod_param('stopmix', [2,2], 'usqmix', [6,6]) 1600 1601 # DSQMIX 1602 card.add_param('dsqmix', [1,1], 1.0) 1603 card.add_param('dsqmix', [2,2], 1.0) 1604 card.add_param('dsqmix', [4,4], 1.0) 1605 card.add_param('dsqmix', [5,5], 1.0) 1606 card.mod_param('sbotmix', [1,1], 'dsqmix', [3,3]) 1607 card.mod_param('sbotmix', [1,2], 'dsqmix', [3,6]) 1608 card.mod_param('sbotmix', [2,1], 'dsqmix', [6,3]) 1609 card.mod_param('sbotmix', [2,2], 'dsqmix', [6,6]) 1610 1611 1612 # SELMIX 1613 card.add_param('selmix', [1,1], 1.0) 1614 card.add_param('selmix', [2,2], 1.0) 1615 card.add_param('selmix', [4,4], 1.0) 1616 card.add_param('selmix', [5,5], 1.0) 1617 card.mod_param('staumix', [1,1], 'selmix', [3,3]) 1618 card.mod_param('staumix', [1,2], 'selmix', [3,6]) 1619 card.mod_param('staumix', [2,1], 'selmix', [6,3]) 1620 card.mod_param('staumix', [2,2], 'selmix', [6,6]) 1621 1622 # FRALPHA 1623 card.mod_param('alpha', [], 'fralpha', [1]) 1624 1625 #HMIX 1626 card.remove_param('hmix', [3]) 1627 1628 # VCKM 1629 card.add_param('vckm', [1,1], 1.0) 1630 card.add_param('vckm', [2,2], 1.0) 1631 card.add_param('vckm', [3,3], 1.0) 1632 1633 #SNUMIX 1634 card.add_param('snumix', [1,1], 1.0) 1635 card.add_param('snumix', [2,2], 1.0) 1636 card.add_param('snumix', [3,3], 1.0) 1637 1638 #UPMNS 1639 card.add_param('upmns', [1,1], 1.0) 1640 card.add_param('upmns', [2,2], 1.0) 1641 card.add_param('upmns', [3,3], 1.0) 1642 1643 # Te 1644 ye = card['ye'].get([1, 1], default=0).value 1645 ae = card['ae'].get([1, 1], default=0).value 1646 card.mod_param('ae', [1,1], 'te', [1,1], value= ae * ye, comment='T_e(Q) DRbar') 1647 if ae * ye: 1648 raise InvalidParamCard, '''This card is not suitable to be converted to MSSM UFO model 1649 Parameter ae [1, 1] times ye [1,1] should be 0''' 1650 card.remove_param('ae', [1,1]) 1651 #2 1652 ye = card['ye'].get([2, 2], default=0).value 1653 1654 ae = card['ae'].get([2, 2], default=0).value 1655 card.mod_param('ae', [2,2], 'te', [2,2], value= ae * ye, comment='T_mu(Q) DRbar') 1656 if ae * ye: 1657 raise InvalidParamCard, '''This card is not suitable to be converted to MSSM UFO model 1658 Parameter ae [2, 2] times ye [2,2] should be 0''' 1659 card.remove_param('ae', [2,2]) 1660 #3 1661 ye = card['ye'].get([3, 3], default=0).value 1662 ae = card['ae'].get([3, 3], default=0).value 1663 card.mod_param('ae', [3,3], 'te', [3,3], value= ae * ye, comment='T_tau(Q) DRbar') 1664 1665 # Tu 1666 yu = card['yu'].get([1, 1], default=0).value 1667 au = card['au'].get([1, 1], default=0).value 1668 card.mod_param('au', [1,1], 'tu', [1,1], value= au * yu, comment='T_u(Q) DRbar') 1669 if au * yu: 1670 raise InvalidParamCard, '''This card is not suitable to be converted to MSSM UFO model 1671 Parameter au [1, 1] times yu [1,1] should be 0''' 1672 card.remove_param('au', [1,1]) 1673 #2 1674 ye = card['yu'].get([2, 2], default=0).value 1675 1676 ae = card['au'].get([2, 2], default=0).value 1677 card.mod_param('au', [2,2], 'tu', [2,2], value= au * yu, comment='T_c(Q) DRbar') 1678 if au * yu: 1679 raise InvalidParamCard, '''This card is not suitable to be converted to MSSM UFO model 1680 Parameter au [2, 2] times yu [2,2] should be 0''' 1681 card.remove_param('au', [2,2]) 1682 #3 1683 yu = card['yu'].get([3, 3]).value 1684 au = card['au'].get([3, 3]).value 1685 card.mod_param('au', [3,3], 'tu', [3,3], value= au * yu, comment='T_t(Q) DRbar') 1686 1687 # Td 1688 yd = card['yd'].get([1, 1], default=0).value 1689 ad = card['ad'].get([1, 1], default=0).value 1690 card.mod_param('ad', [1,1], 'td', [1,1], value= ad * yd, comment='T_d(Q) DRbar') 1691 if ad * yd: 1692 raise InvalidParamCard, '''This card is not suitable to be converted to MSSM UFO model 1693 Parameter ad [1, 1] times yd [1,1] should be 0''' 1694 card.remove_param('ad', [1,1]) 1695 #2 1696 ye = card['yd'].get([2, 2], default=0).value 1697 1698 ae = card['ad'].get([2, 2], default=0).value 1699 card.mod_param('ad', [2,2], 'td', [2,2], value= ad * yd, comment='T_s(Q) DRbar') 1700 if ad * yd: 1701 raise InvalidParamCard, '''This card is not suitable to be converted to MSSM UFO model 1702 Parameter ad [2, 2] times yd [2,2] should be 0''' 1703 card.remove_param('ad', [2,2]) 1704 #3 1705 yd = card['yd'].get([3, 3]).value 1706 ad = card['ad'].get([3, 3]).value 1707 card.mod_param('ad', [3,3], 'td', [3,3], value= ad * yd, comment='T_b(Q) DRbar') 1708 1709 1710 # MSL2 1711 value = card['msoft'].get([31]).value 1712 card.mod_param('msoft', [31], 'msl2', [1,1], value**2) 1713 value = card['msoft'].get([32]).value 1714 card.mod_param('msoft', [32], 'msl2', [2,2], value**2) 1715 value = card['msoft'].get([33]).value 1716 card.mod_param('msoft', [33], 'msl2', [3,3], value**2) 1717 1718 # MSE2 1719 value = card['msoft'].get([34]).value 1720 card.mod_param('msoft', [34], 'mse2', [1,1], value**2) 1721 value = card['msoft'].get([35]).value 1722 card.mod_param('msoft', [35], 'mse2', [2,2], value**2) 1723 value = card['msoft'].get([36]).value 1724 card.mod_param('msoft', [36], 'mse2', [3,3], value**2) 1725 1726 # MSQ2 1727 value = card['msoft'].get([41]).value 1728 card.mod_param('msoft', [41], 'msq2', [1,1], value**2) 1729 value = card['msoft'].get([42]).value 1730 card.mod_param('msoft', [42], 'msq2', [2,2], value**2) 1731 value = card['msoft'].get([43]).value 1732 card.mod_param('msoft', [43], 'msq2', [3,3], value**2) 1733 1734 # MSU2 1735 value = card['msoft'].get([44]).value 1736 card.mod_param('msoft', [44], 'msu2', [1,1], value**2) 1737 value = card['msoft'].get([45]).value 1738 card.mod_param('msoft', [45], 'msu2', [2,2], value**2) 1739 value = card['msoft'].get([46]).value 1740 card.mod_param('msoft', [46], 'msu2', [3,3], value**2) 1741 1742 # MSD2 1743 value = card['msoft'].get([47]).value 1744 card.mod_param('msoft', [47], 'msd2', [1,1], value**2) 1745 value = card['msoft'].get([48]).value 1746 card.mod_param('msoft', [48], 'msd2', [2,2], value**2) 1747 value = card['msoft'].get([49]).value 1748 card.mod_param('msoft', [49], 'msd2', [3,3], value**2) 1749 1750 ################# 1751 # WRITE OUTPUT 1752 ################# 1753 if writting: 1754 card.write(outputpath) 1755 return card
1756
1757 1758 -def make_valid_param_card(path, restrictpath, outputpath=None):
1759 """ modify the current param_card such that it agrees with the restriction""" 1760 1761 if not outputpath: 1762 outputpath = path 1763 1764 cardrule = ParamCardRule() 1765 cardrule.load_rule(restrictpath) 1766 try : 1767 cardrule.check_param_card(path, modify=False) 1768 except InvalidParamCard: 1769 new_data, was_modified = cardrule.check_param_card(path, modify=True, write_missing=True) 1770 if was_modified: 1771 cardrule.write_param_card(outputpath, new_data) 1772 else: 1773 if path != outputpath: 1774 shutil.copy(path, outputpath) 1775 return cardrule
1776
1777 -def check_valid_param_card(path, restrictpath=None):
1778 """ check if the current param_card agrees with the restriction""" 1779 1780 if restrictpath is None: 1781 restrictpath = os.path.dirname(path) 1782 restrictpath = os.path.join(restrictpath, os.pardir, os.pardir, 'Source', 1783 'MODEL', 'param_card_rule.dat') 1784 if not os.path.exists(restrictpath): 1785 restrictpath = os.path.dirname(path) 1786 restrictpath = os.path.join(restrictpath, os.pardir, 'Source', 1787 'MODEL', 'param_card_rule.dat') 1788 if not os.path.exists(restrictpath): 1789 return True 1790 1791 cardrule = ParamCardRule() 1792 cardrule.load_rule(restrictpath) 1793 cardrule.check_param_card(path, modify=False)
1794 1795 1796 1797 if '__main__' == __name__: 1798 1799 1800 #make_valid_param_card('./Cards/param_card.dat', './Source/MODEL/param_card_rule.dat', 1801 # outputpath='tmp1.dat') 1802 import sys 1803 args = sys.argv 1804 sys.path.append(os.path.dirname(__file__)) 1805 convert_to_slha1(args[1] , args[2]) 1806