NREL / floris

A controls-oriented engineering wake model.
http://nrel.github.io/floris
BSD 3-Clause "New" or "Revised" License
215 stars 156 forks source link

[BUG] Missed dimension reduction in `YawOptimization` base class #1033

Open misi9170 opened 2 days ago

misi9170 commented 2 days ago

These lines

        idx = (minimum_yaw_angle_subset > 0.0) | (maximum_yaw_angle_subset < 0.0)
        if np.any(idx):
            # Find bounds closest to 0.0 deg
            combined_bounds = np.concatenate(
                (
                    np.expand_dims(minimum_yaw_angle_subset, axis=3),
                    np.expand_dims(maximum_yaw_angle_subset, axis=3)
                ),
                axis=3
            )
            # Overwrite all values that are not allowed to be 0.0 with bound value closest to zero
            ids_closest = np.expand_dims(np.argmin(np.abs(combined_bounds), axis=3), axis=3)
            yaw_mb = np.squeeze(np.take_along_axis(combined_bounds, ids_closest, axis=3))
            yaw_angles_template_subset[idx] = yaw_mb[idx]

were missed in the v4 dimension reduction process #764 , and can be fixed by replacing with

        idx = (minimum_yaw_angle_subset > 0.0) | (maximum_yaw_angle_subset < 0.0)
        if np.any(idx):
            # Find bounds closest to 0.0 deg
            combined_bounds = np.concatenate(
                (
                    np.expand_dims(minimum_yaw_angle_subset, axis=2),
                    np.expand_dims(maximum_yaw_angle_subset, axis=2)
                ),
                axis=2
            )
            # Overwrite all values that are not allowed to be 0.0 with bound value closest to zero
            ids_closest = np.expand_dims(np.argmin(np.abs(combined_bounds), axis=2), axis=2)
            yaw_mb = np.squeeze(np.take_along_axis(combined_bounds, ids_closest, axis=2), axis=2)
            yaw_angles_template_subset[idx] = yaw_mb[idx]

(that is, switching from axis=3 to axis=2 throughout, and also specifying the axis for the np.squeeze operation).

The reason this hasn't come up before is that this code only runs if minimum_yaw_angle is strictly greater 0 or maximum_yaw_angle is strictly less than 0, which is an unusual circumstance.

I will create a bugfix PR in due course that will include tests for these "unusual" minimum and maximum angles.