thegrumpys / odop

Open Design Optimization Platform (ODOP) - Coil spring design app; mechanical springs; compression spring, extension spring, torsion spring
https://www.springdesignsoftware.org
MIT License
4 stars 5 forks source link

Usage log entries for Objective Values of infinity and NaN #768

Open grumpyinca opened 1 year ago

grumpyinca commented 1 year ago

In theory, the code of the various design types (init, eqnset) is sufficiently well protected to never generate infinity and NaN Objective Function values. In practice, that may not be true. Generating usage log entries when these values result from user input or Search Seek & Trade would help in rapid identification of these cases if and when they exist.

1fifoto commented 1 year ago

We have investigated this change. Each time the objective value, obj, is calculated in either pxUpdateObjectiveValue or updateObjectiveValue. we felt that it should check to see if the objective value isNaN(obj) or not isFinite(obj). However the pxUpdateObjectiveValue function is called during search and logUsage should not be added to this function. Instead we attempted to add these checks to updateObjectiveValue. We test this by setting Wire_Dia=0.1 and OD_Free=0.2. The resulting objective value (via the status message) showed it to be 'infinite'. Looking into the usage log we found multiple entries (actually 6 of them, one after the other) for the single change. This was puzzling and we were unable to resolve why this was happening. So further investigation should be done so that this change only creates only one usage log entry.

Here is the modified updateObjectiveValue change showing the if (isNaN(obj)) {...} else if (!isFinite(obj)) {...}

// Update Objective Value
obj = design.model.system_controls.viol_wt * viol_sum + m_funct;
store.dispatch(changeResultObjectiveValue(obj));
store.dispatch(changeResultSearchCompleted(false));
if (isNaN(obj)) {
    logUsage('event', 'UpdateObjectiveValue', { event_label: 'NaN ' + obj});
    console.log('UpdateObjectiveValue NaN');
} else if (!isFinite(obj)) {
    logUsage('event', 'UpdateObjectiveValue', { event_label: 'Infinite ' + obj});
    console.log('UpdateObjectiveValue Infinite');
}

Brian believes that the linkage between the Redux reducers (which updates something in the model) and their counterparts in the Redux dispatchers (which attempt to make sure these updates cascade to the entire model) is the problem. Brian thought that we should create a flag that indicates the objective value should be re-computed. Mike suggested that this be called the 'dirty' bit. In other words, today as model changes are made there is a cascade of other model changes such as the objective value calculation. Unfortunately this is done multiple times for a single primary model change. However, if a 'dirty' bit can be implemented, the multiple times could be deferred to the end and done only once.