def calculate_weights_spn(correlations, covariance):
    """Calculate SPN blending weights for STEPS blending from correlation.

    Parameters
    ----------
    correlations : array-like
      Array of shape [n_components]
      containing correlation (skills) for each component (NWP models and nowcast).
    covariance : array-like
        Array of shape [n_components, n_components] containing the covariance
        matrix of the models that will be blended. If cov is set to None and
        correlations only contains one model, the weight equals the correlation
        on that scale level and the noise component weight equals 1 - this weight.

    Returns
    -------
    weights : array-like
      Array of shape [component+1]
      containing the weights to be used in STEPS blending for each original
      component plus an addtional noise component.

    References
    ----------
    :cite:`SPN2013`
    """
    # Check if the correlations are positive, otherwise rho = 10e-5
    correlations = np.where(correlations < 10e-5, 10e-5, correlations)

    if correlations.shape[0] > 1 and len(covariance) > 1:
        if isinstance(covariance, type(None)):
            raise ValueError("cov must contain a covariance matrix")
        else:
            # Make a numpy array out of cov and get the inverse
            covariance = np.where(covariance == 0.0, 10e-5, covariance)
            # Make sure the determinant of the matrix is not zero, otherwise
            # subtract 10e-5 from the cross-correlations between the models
            if np.linalg.det(covariance) == 0.0:
                covariance = covariance - 10e-5
            # Ensure the correlation of the model with itself is always 1.0
            for i, _ in enumerate(covariance):
                covariance[i][i] = 1.0
            # Use a numpy array instead of a matrix
            cov_matrix = np.array(covariance)
            # Get the inverse of the matrix using scipy's inv function
            cov_matrix_inv = inv(cov_matrix)
            # The component weights are the dot product between cov_matrix_inv and cor_vec
            weights = np.dot(cov_matrix_inv, correlations)
            weights = np.nan_to_num(
                weights, copy=True, nan=10e-5, posinf=10e-5, neginf=10e-5
            )
            weights_dot_correlations = np.dot(weights, correlations)
            # If the dot product of the weights with the correlations is
            # larger than 1.0, we assign a weight of 0.0 to the noise (to make
            # it numerically stable)
            if weights_dot_correlations > 1.0:
                noise_weight = np.array([0])
            # Calculate the noise weight
            else:
                noise_weight = np.sqrt(1.0 - weights_dot_correlations)
            # Convert weights to a 1D array
            weights = np.array(weights).flatten()
            # Ensure noise_weight is a 1D array before concatenation
            noise_weight = np.array(noise_weight).flatten()
            # Finally, add the noise_weights to the weights variable.
            weights = np.concatenate((weights, noise_weight), axis=0)

    # Otherwise, the weight equals the correlation on that scale level and
    # the noise component weight equals 1 - this weight. This only occurs for
    # the weights calculation outside the radar domain where in the case of 1
    # NWP model or ensemble member, no blending of multiple models has to take
    # place
    else:
        noise_weight = 1.0 - correlations
        weights = np.concatenate((correlations, noise_weight), axis=0)

    # Make sure weights are always a real number
    weights = np.nan_to_num(weights, copy=True, nan=10e-5, posinf=10e-5, neginf=10e-5)

    return weights
Calculate SPN blending weights for STEPS blending from correlation.

Parameters
----------
correlations : array-like
Array of shape [n_components]
containing correlation (skills) for each component (NWP models and nowcast).
covariance : array-like
Array of shape [n_components, n_components] containing the covariance
matrix of the models that will be blended. If cov is set to None and
correlations only contains one model, the weight equals the correlation
on that scale level and the noise component weight equals 1 - this weight.

Returns
-------
weights : array-like
Array of shape [component+1]
containing the weights to be used in STEPS blending for each original
component plus an addtional noise component.

References
----------
:cite:`SPN2013`
pysteps/blending/steps.py