Skip to content

[fix] Corrected/enhanced merger process#785

Open
ezapartas wants to merge 14 commits intomainfrom
manos_merger_copiedattributes
Open

[fix] Corrected/enhanced merger process#785
ezapartas wants to merge 14 commits intomainfrom
manos_merger_copiedattributes

Conversation

@ezapartas
Copy link
Contributor

Implementing and solving issues already discussed in a previous PR version #311 which is now deprecated.

  • No deepcopy during merger (which was working, but led to memory and speed issues)
  • However, correct caclulations of the mass weighted averages of abundances BEFORE mass changes.
  • calculating center_gamma and avg_c_in_c_core for mergers whenever possible (as the core value if the cores do not merge and np.nap and mass-weighted average respectively, if the cores merge).
  • added co_core_mass as a potential option in the matching criteria at track_match (mostly for mergers)

Reminder : The resulting merger product is continuing as a singlestar instance at the place of the engulfing star (i.e. if oMerging1, then star_1 would be the merged product) UNLESS a NS/BH is involved, where the latter is the only one surviving (potential Thorne-Zytkov object).

@ezapartas ezapartas requested review from maxbriel and sgossage and removed request for sgossage January 15, 2026 14:39
try:
mass_weighted_avg_value=(A1*M1+A2*M2)/(M1+M2)
except TypeError:
mass_weighted_avg_value= np.nan
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is setting the mass weighted average to np.nan going to cause issues later down the pipeline?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it possible to avoid a try/except?
Is it instead possible to verify the type of the values used?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  1. @astro-abhishek the np.nan may cause issues later, but I think is the most pythonic way of saying "the function was called byt physically there are issues at the calculation so we have no computed result, we don't know the value". If the question is whether it will make it crash, I am not sure, I think not, as np.nan is accepted as a value in calculations, it will just produce more "unknown" np.nan quantities wherever it is used in a calcualation.

  2. @maxbriel The following is a different way more exact checking, instead of try-except loop. Is this what you are thinking? If did not add it yet, but if you agree, please just add it as a commit directly.

den = M1 + M2
if not (np.isfinite(A1) and np.isfinite(A2) and np.isfinite(M1) and np.isfinite(M2)):
mass_weighted_avg_value = np.nan
elif den == 0:
mass_weighted_avg_value = np.nan
else:
mass_weighted_avg_value = (A1M1 + A2M2) / den


In both cases, if you have better coding ideas for this part (or any other) feel free to add them directly.

"log_R",
"center_c12"
"center_c12",
"co_core_mass"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

what if the co_core_mass doesn't exist? (there's a comment about something similar right above this)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm, this list assumes that the single star models and the respective EEPs have this column. If a user uses their one sinlge star and EEPs, not run with POSYDON, so not calculating a co_core (having only a c_core or an o_core for example), there may be a mismatch. For our POSYDON runs this is ok for now. If we want to generalize it so much, I think much of the structure should change anyway. I would leave it for now, keeping the above comment there for future reference.

@maxbriel maxbriel changed the title Corrected/enhanced merger process [fix] Corrected/enhanced merger process Feb 9, 2026
@maxbriel
Copy link
Collaborator

maxbriel commented Feb 9, 2026

There are two testing binaries in the suite that change with this PR.
@ezapartas can you confirm that these changes are expected from the change in the PR?

image image


# weighted central abundances if merging cores. Else only from star_base
if (comp.co_core_mass > 0 and star_base.co_core_mass == 0): # comp with CO core and the star_base has not
if (comp.co_core_mass is not None and star_base.co_core_mass == 0): # comp with CO core and the star_base has not
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is there this change from values to None? It happens later too.

Are there specific binaries that crash because the co_core_mass is undefined when reaching this stage?

Same n line 575.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm, I don' remember exactly the reasoning. I think I thought that instead of raising a TypeError in case of comp.co_core_mass = None and crashing, I preferred it to go to the else: Pwarn("weird compbination of CO core masses during merging", "EvolutionWarning").

But again, if you think of a better handling it , feel free to directly change it back

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is this TODO still needed?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, you are right, I took the line out

for key in ["mass", "he_core_mass", "c_core_mass", "o_core_mass", "co_core_mass"]:
current = getattr(star_base, key) + getattr(comp, key)
setattr(merged_star, key,current)
merged_star = comp
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why are we changing what the merged star is here?

This is different than the definition of which one starts the RLO. This will make the companion the remaining star.

Copy link
Contributor Author

@ezapartas ezapartas Feb 12, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm, actually this occurs even at line 256. Indeed, it "violates" the engulfind star (that starts the RLO) is our base of the merger, making the base to be the star with the most layers. So for example in a postMS+HMS merger, the postMS star becomes the base always. Same between postMS+HeMS. Even if it is not the postMS that engulfs. This is because the final merged star with have a more complex layering (envelope, core, etc). Of course in most cases it will indeed be the postMS star that is also initiating the RLO and the engulfing, but we allow for the other case too, giving the same outcome.

If needed we can restructure the code to remake the calculation using the engulfing always as the base, but this is only for the sake of clarity. It will not change the merged outcome in the end.

summary: The outcome in the end should not depend on which star engulfs (unless omeone argues otherwise). it is just easier to start the merger construction from that star in most cases, as it usually is the more "complex" star in the perspective of layers, i.e. it is a giant star

@maxbriel maxbriel added enhancement New feature or request bug Something isn't working labels Feb 10, 2026
@ezapartas
Copy link
Contributor Author

@astro-abhishek @maxbriel Thanks for the detailed comments. I tried to answer all of them and address whichever where doable. Feel free to directly change the coding way if you think a better option exists.

Note as soon as this PR is accepted, it is better to be pulled by the #788 before that PR is evaluated and merged.

merged_star.avg_c_in_c_core = mass_weighted_avg(abundance_name = "avg_c_in_c_core", mass_weight1="he_core_mass")
merged_star.center_n14 = mass_weighted_avg(abundance_name = "center_n14", mass_weight1="he_core_mass")
merged_star.center_o16 = mass_weighted_avg(abundance_name = "center_o16", mass_weight1="he_core_mass")
setattr(merged_star, "center_gamma", np.nan)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we not use the parameters of the helium stars to set center_gamma?

merged_star.avg_c_in_c_core = mass_weighted_avg(abundance_name = "avg_c_in_c_core", mass_weight1="co_core_mass")
merged_star.center_n14 = mass_weighted_avg(abundance_name = "center_n14", mass_weight1="co_core_mass")
merged_star.center_o16 = mass_weighted_avg(abundance_name = "center_o16", mass_weight1="co_core_mass")
setattr(merged_star, "center_gamma", np.nan)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same comment as above about center_gamma

merged_star.avg_c_in_c_core = mass_weighted_avg(abundance_name = "avg_c_in_c_core", mass_weight1="he_core_mass")
merged_star.center_n14 = mass_weighted_avg(abundance_name = "center_n14", mass_weight1="he_core_mass")
merged_star.center_o16 = mass_weighted_avg(abundance_name = "center_o16", mass_weight1="he_core_mass")
setattr(merged_star, "center_gamma", np.nan)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same comment as above. Why set to nan instead of grabbing the value from either star_base or comp?

merged_star.avg_c_in_c_core = mass_weighted_avg(abundance_name = "avg_c_in_c_core", mass_weight1="he_core_mass")
merged_star.center_n14 = mass_weighted_avg(abundance_name = "center_n14", mass_weight1="he_core_mass")
merged_star.center_o16 = mass_weighted_avg(abundance_name = "center_o16", mass_weight1="he_core_mass")
setattr(merged_star, "center_gamma", np.nan)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See above

merged_star.avg_c_in_c_core = mass_weighted_avg(abundance_name = "avg_c_in_c_core", mass_weight1="co_core_mass")
merged_star.center_n14 = mass_weighted_avg(abundance_name = "center_n14", mass_weight1="co_core_mass")
merged_star.center_o16 = mass_weighted_avg(abundance_name = "center_o16", mass_weight1="co_core_mass")
setattr(merged_star, "center_gamma", np.nan)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

see above

merged_star.avg_c_in_c_core = mass_weighted_avg(abundance_name = "avg_c_in_c_core", mass_weight1="he_core_mass")
merged_star.center_n14 = mass_weighted_avg(abundance_name = "center_n14", mass_weight1="he_core_mass")
merged_star.center_o16 = mass_weighted_avg(abundance_name = "center_o16", mass_weight1="he_core_mass")
setattr(merged_star, "center_gamma", np.nan)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

see above

merged_star.avg_c_in_c_core = mass_weighted_avg(abundance_name = "avg_c_in_c_core", mass_weight1="he_core_mass")
merged_star.center_n14 = mass_weighted_avg(abundance_name = "center_n14", mass_weight1="he_core_mass")
merged_star.center_o16 = mass_weighted_avg(abundance_name = "center_o16", mass_weight1="he_core_mass")
setattr(merged_star, "center_gamma", np.nan)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

see above

merged_star.avg_c_in_c_core = mass_weighted_avg(abundance_name = "avg_c_in_c_core", mass_weight1="co_core_mass")
merged_star.center_n14 = mass_weighted_avg(abundance_name = "center_n14", mass_weight1="co_core_mass")
merged_star.center_o16 = mass_weighted_avg(abundance_name = "center_o16", mass_weight1="co_core_mass")
setattr(merged_star, "center_gamma", np.nan)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

see above

@astroJeff
Copy link
Contributor

Can we spin off some of this into new functions? There is quite a bit of repeated code

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working enhancement New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

Comments