scikit-hep / decaylanguage

Package to parse decay files, describe and convert particle decays between digital representations.
https://decaylanguage.readthedocs.io
BSD 3-Clause "New" or "Revised" License
42 stars 16 forks source link

`MyDecFileParser.print_decay_modes` ommits decays if BF is equal to others #451

Closed manuelfs closed 1 month ago

manuelfs commented 1 month ago

When printing a .dec file such as

Decay B0sig
0.01    MyD*-    MyD_s+   pi0                    PHOTOS  ISGW2;
0.01    MyD*-    MyD_s+   pi+  pi-               PHOTOS  ISGW2;
0.01    MyD*-    MyD_s*+  pi+  pi-               PHOTOS  ISGW2;

0.001  MyD_2*-  MyD_s*+  pi0  pi0               PHOTOS  ISGW2;
0.001  MyD_2*-  MyD_s+   pi+  pi-               PHOTOS  ISGW2;
0.001  MyD_2*-  MyD_s*+  pi+  pi-               PHOTOS  ISGW2;
Enddecay
End

with the code

    parser = MyDecFileParser(dec_file)
    parser.parse()

    decays = list_complement(parser.list_decay_mother_names(),
                             parser.list_charge_conjugate_decays())

    for d in decays:
        print('Decay {}'.format(d))
        parser.print_decay_modes(d)

you get

Decay B0sig
  0.9090909091      MyD*-   MyD_s*+ pi+ pi-     PHOTOS ISGW2;
  0.09090909091     MyD_2*- MyD_s*+ pi+ pi-     PHOTOS ISGW2;

Trying different things, I found out that this is because, when there are several decays with the same BF, it only prints the last one.

eduardo-rodrigues commented 1 month ago

Hello @manuelfs, thank you for reporting. This is strange, even more because of the little reproducer below - you seem to be using some private code and better have a simple and "standard" reproducer:

In [1]: from decaylanguage import DecFileParser

In [2]: dfp = DecFileParser.from_string("""Decay B0sig
   ...: 0.01    MyD*-    MyD_s+   pi0                    PHOTOS  ISGW2;
   ...: 0.01    MyD*-    MyD_s+   pi+  pi-               PHOTOS  ISGW2;
   ...: 0.01    MyD*-    MyD_s*+  pi+  pi-               PHOTOS  ISGW2;
   ...:
   ...: 0.001  MyD_2*-  MyD_s*+  pi0  pi0               PHOTOS  ISGW2;
   ...: 0.001  MyD_2*-  MyD_s+   pi+  pi-               PHOTOS  ISGW2;
   ...: 0.001  MyD_2*-  MyD_s*+  pi+  pi-               PHOTOS  ISGW2;
   ...: Enddecay
   ...: End
   ...: """)

In [3]: dfp.parse()

In [4]: dfp.print_decay_modes("B0sig")
  0.01              MyD*-   MyD_s*+ pi+ pi-     PHOTOS ISGW2;
  0.001             MyD_2*- MyD_s*+ pi+ pi-     PHOTOS ISGW2;

In [5]: dfp.list_decay_modes("B0sig")
Out[5]:
[['MyD*-', 'MyD_s+', 'pi0'],
 ['MyD*-', 'MyD_s+', 'pi+', 'pi-'],
 ['MyD*-', 'MyD_s*+', 'pi+', 'pi-'],
 ['MyD_2*-', 'MyD_s*+', 'pi0', 'pi0'],
 ['MyD_2*-', 'MyD_s+', 'pi+', 'pi-'],
 ['MyD_2*-', 'MyD_s*+', 'pi+', 'pi-']]

So list_decay_modes is fine whereas print_decay_modes isn't. This being said, they use a fair bit of common internal code. There must a buglet going on with ordering or alike ...

I'm about to be unavailable for a few days. Contributions are super welcome. Maybe you can debug and create a contribution with the fix and a test for it based on my little reproducer? That would be super :-).

manuelfs commented 1 month ago

All right, I took a stab at it https://github.com/scikit-hep/decaylanguage/pull/452