Compute the limiting SLH model for the adiabatic approximation

    Args:
        YABFGN: The tuple (Y, A, B, F, G, N)
            as returned by prepare_adiabatic_limit.
        Ytilde: The pseudo-inverse of Y, satisfying Y * Ytilde = P0.
        P0: The projector onto the null-space of Y.

    Returns:
        SLH: Limiting SLH model

def eval_adiabatic_limit(YABFGN, Ytilde, P0):
    """Compute the limiting SLH model for the adiabatic approximation

    Args:
        YABFGN: The tuple (Y, A, B, F, G, N)
            as returned by prepare_adiabatic_limit.
        Ytilde: The pseudo-inverse of Y, satisfying Y * Ytilde = P0.
        P0: The projector onto the null-space of Y.

    Returns:
        SLH: Limiting SLH model
    """
    Y, A, B, F, G, N = YABFGN

    Klim = (P0 * (B - A * Ytilde * A) * P0).expand().simplify_scalar()
    Hlim = ((Klim - Klim.dag())/2/I).expand().simplify_scalar()

    Ldlim = (P0 * (G - A * Ytilde * F) * P0).expand().simplify_scalar()

    dN = identity_matrix(N.shape[0]) + F.H * Ytilde * F
    Nlim = (P0 * N * dN * P0).expand().simplify_scalar()

    return SLH(Nlim.dag(), Ldlim.dag(), Hlim.dag())