1
################################################################################
3
# Copyright (c) 2009 The MadGraph Development team and Contributors
5
# This file is a part of the MadGraph 5 project, an application which
6
# automatically generates Feynman diagrams and matrix elements for arbitrary
7
# high-energy processes in the Standard Model and beyond.
9
# It is subject to the MadGraph license which should accompany this
12
# For more information, please visit: http://madgraph.phys.ucl.ac.be
14
################################################################################
15
"""Methods and classes to group subprocesses according to initial
16
states, and produce the corresponding grouped subprocess directories."""
26
import madgraph.core.base_objects as base_objects
27
import madgraph.core.diagram_generation as diagram_generation
28
import madgraph.core.helas_objects as helas_objects
29
import madgraph.iolibs.drawing_eps as draw
30
import madgraph.iolibs.files as files
31
import madgraph.iolibs.misc as misc
32
import madgraph.iolibs.file_writers as writers
33
import madgraph.iolibs.template_files as template_files
34
import madgraph.iolibs.ufo_expression_parsers as parsers
36
import aloha.create_aloha as create_aloha
38
import models.sm.write_param_card as write_param_card
39
from madgraph import MadGraph5Error, MG5DIR
40
from madgraph.iolibs.files import cp, ln, mv
41
_file_path = os.path.split(os.path.dirname(os.path.realpath(__file__)))[0] + '/'
42
logger = logging.getLogger('madgraph.export_v4')
44
#===============================================================================
46
#===============================================================================
48
class SubProcessGroup(base_objects.PhysicsObject):
49
"""Class to group a number of amplitudes with same initial states
50
into a subprocess group"""
52
def default_setup(self):
53
"""Define object and give default values"""
57
self['amplitudes'] = diagram_generation.AmplitudeList()
58
self['mapping_diagrams'] = []
59
self['diagram_maps'] = {}
60
self['matrix_elements'] = helas_objects.HelasMultiProcess()
62
def filter(self, name, value):
63
"""Filter for valid property values."""
66
if not isinstance(value, int):
67
raise self.PhysicsObjectError, \
68
"%s is not a valid int object" % str(value)
70
if not isinstance(value, str):
71
raise self.PhysicsObjectError, \
72
"%s is not a valid str object" % str(value)
73
if name == 'amplitudes':
74
if not isinstance(value, diagram_generation.AmplitudeList):
75
raise self.PhysicsObjectError, \
76
"%s is not a valid amplitudelist" % str(value)
77
if name == 'mapping_diagrams':
78
if not isinstance(value, list):
79
raise self.PhysicsObjectError, \
80
"%s is not a valid list" % str(value)
81
if name == 'diagram_maps':
82
if not isinstance(value, dict):
83
raise self.PhysicsObjectError, \
84
"%s is not a valid dict" % str(value)
85
if name == 'matrix_elements':
86
if not isinstance(value, helas_objects.HelasMultiProcess):
87
raise self.PhysicsObjectError, \
88
"%s is not a valid HelasMultiProcess" % str(value)
91
def get_sorted_keys(self):
92
"""Return diagram property names as a nicely sorted list."""
94
return ['number', 'name', 'amplitudes', 'mapping_diagrams',
95
'diagram_maps', 'matrix_elements']
97
# Enhanced get function
99
"""Get the value of the property name."""
101
if name == 'matrix_elements' and not self[name].get('matrix_elements'):
102
self.generate_matrix_elements()
104
if name in ['mapping_diagrams', 'diagram_maps'] and not self[name]:
105
self.set_mapping_diagrams()
107
return super(SubProcessGroup, self).get(name)
109
def set_mapping_diagrams(self):
110
"""Set mapping_diagrams and diagram_maps, to prepare for
111
generation of the super-config.inc files."""
113
if not self.get('amplitudes'):
114
raise self.PhysicsObjectError, \
115
"Need amplitudes to set mapping_diagrams"
117
# All amplitudes are already in the same class
118
process_classes = dict([(i, 0) for i in \
119
range(len(self.get('amplitudes')))])
120
mapping_diagrams, diagram_maps = \
121
self.get('amplitudes').find_mapping_diagrams(process_classes, 0)
123
self.set('mapping_diagrams', mapping_diagrams)
124
self.set('diagram_maps', diagram_maps)
126
def generate_matrix_elements(self):
127
"""Create a HelasMultiProcess corresponding to the amplitudes
130
if not self.get('amplitudes'):
131
raise self.PhysicsObjectError, \
132
"Need amplitudes to generate matrix_elements"
134
self.set_mapping_diagrams()
136
self['matrix_elements'] = helas_objects.HelasMultiProcess(\
137
self.get('amplitudes'))
139
self.rearrange_diagram_maps()
141
def rearrange_diagram_maps(self):
142
"""Rearrange the diagram_maps according to the matrix elements in
143
the HelasMultiProcess"""
145
amplitude_map = self.get('matrix_elements').get('amplitude_map')
146
new_diagram_maps = {}
147
for key in amplitude_map:
148
new_diagram_maps[amplitude_map[key]] = self.get('diagram_maps')[key]
150
self.set("diagram_maps", new_diagram_maps)
153
def group_amplitudes(amplitudes):
154
"""Return a SubProcessGroupList with the amplitudes divided
155
into subprocess groups"""
157
if not isinstance(amplitudes, diagram_generation.AmplitudeList):
158
raise SubProcessGroupList.PhysicsObjectError, \
159
"Argument to group_amplitudes must be AmplitudeList"
161
process_classes = amplitudes.find_process_classes()
162
ret_list = SubProcessGroupList()
163
process_class_numbers = sorted(list(set(process_classes.values())))
164
for inum, num in enumerate(process_class_numbers):
165
amp_nums = [key for (key, val) in process_classes.items() if \
167
group = SubProcessGroup()
168
group.set('number', inum+1)
169
group.set('amplitudes',
170
diagram_generation.AmplitudeList([amplitudes[i] for i in \
172
ret_list.append(group)
176
#===============================================================================
177
# SubProcessGroupList
178
#===============================================================================
179
class SubProcessGroupList(base_objects.PhysicsObjectList):
180
"""List of SubProcessGroup objects"""
182
def is_valid_element(self, obj):
183
"""Test if object obj is a valid element."""
185
return isinstance(obj, SubProcessGroup)