use pyo3::prelude::*;

/// Finds subsets sum of a target value. It can accept negative values.
/// # Arguments
/// * `arr` - An array.
/// * `value` - The value to the sum of the subset comes.
/// * `max_length` - The maximum length of combinations of the answer.
#[pyfunction]
#[pyo3(text_signature = "(arr, value, max_length, /)")]
fn find_subset(arr: Vec<i32>, value: i32, max_length: usize) -> PyResult<Vec<Vec<i32>>> {
    use crate::dp_module::*;
    Ok(dp::find_subset(arr, value, max_length))
}


/// Finds the integers from two vectors that sum to the same value.
/// This method assumes that the two vectors have Many-to-Many relationships.
/// Each integer of the `keys` vector corresponds to the multiple integers of the `targets` vector.
/// With this method, we can find combinations of the integers.
/// # Arguments
/// * `keys` - An array.
/// * `targets` - An array.
/// * `max_key_length` - An integer.
/// * `max_target_length` - An integer.
/// * `n_candidates` - An integer.
#[pyfunction]
#[pyo3(text_signature = "(keys, targets, max_key_length, max_target_length, n_candidates /)")]
fn sequence_matcher(
    mut keys: Vec<i32>,
    mut targets: Vec<i32>,
    max_key_length: usize,
    max_target_length: usize,
    n_candidates: usize,
) -> PyResult<Vec<Vec<(Vec<i32>, Vec<i32>)>>> {
    use crate::dp_module::*;
    Ok(dp::sequence_matcher(
        &mut keys,
        &mut targets,
        max_key_length,
        max_target_length,
        n_candidates,
    ))
}

#[pymodule]
fn dpss(_py: Python, m: &PyModule) -> PyResult<()> {
    m.add_function(wrap_pyfunction!(find_subset, m)?)?;
    m.add_function(wrap_pyfunction!(sequence_matcher, m)?)?;
    m.add("__version__", env!("CARGO_PKG_VERSION"))?;

    Ok(())
}
