dpss/
dp_module.rs

1pub mod dp {
2    //! This is a module for dynamic programming.
3
4    use itertools::structs::Combinations;
5    use std::sync::RwLock;
6    use field_accessor::FieldAccessor;
7
8    struct MultiCombination<I: Iterator> {
9        combs: Vec<Combinations<I>>,
10    }
11
12    impl<I> Iterator for MultiCombination<I>
13    where
14        I: Iterator,
15        I::Item: Clone,
16    {
17        type Item = Vec<I::Item>;
18        fn next(&mut self) -> Option<Self::Item> {
19            for comb in &mut self.combs {
20                if let Some(elt) = comb.next() {
21                    return Some(elt);
22                } else {
23                    continue;
24                }
25            }
26            None
27        }
28    }
29    use rayon::prelude::*;
30    use std::collections::HashMap;
31    use std::sync::Arc;
32
33    #[derive(Clone, Debug, FieldAccessor)]
34    pub struct AnswerElement {
35        pub answer_arr: Vec<(Vec<i32>, Vec<i32>)>,
36        pub keys_remainder: Vec<i32>,
37        pub targets_remainder: Vec<i32>,
38    }
39
40    impl Eq for AnswerElement {}
41
42    impl PartialEq for AnswerElement {
43        fn eq(&self, other: &Self) -> bool {
44            self.answer_arr == other.answer_arr
45        }
46    }
47
48    use std::cmp::Ordering;
49
50    impl Ord for AnswerElement {
51        fn cmp(&self, other: &Self) -> Ordering {
52            self.answer_arr.cmp(&other.answer_arr)
53        }
54    }
55
56    impl PartialOrd for AnswerElement {
57        fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
58            Some(self.cmp(other))
59        }
60    }
61
62    #[derive(Clone, Debug)]
63    struct DpTable {
64        dp: Vec<bool>,
65        max_value: usize,
66    }
67
68    pub fn sequence_matcher_formatter(result: Vec<AnswerElement>) -> String {
69        let mut s: Vec<String> = vec![];
70        for (i, r) in result.iter().enumerate() {
71            let mut t: Vec<String> = vec![];
72            for elem in r.answer_arr.clone() {
73                let key_str: String = elem
74                    .0
75                    .iter()
76                    .map(|k| k.to_string())
77                    .collect::<Vec<String>>()
78                    .join(" + ");
79                let target_str: String = elem
80                    .1
81                    .iter()
82                    .map(|k| k.to_string())
83                    .collect::<Vec<String>>()
84                    .join(" + ");
85                t.push(format!(
86                    "(Sum({}) -> keys:[{}] == targets:[{}])",
87                    elem.0.iter().sum::<i32>(),
88                    key_str,
89                    target_str
90                ));
91            }
92            s.push(format!(
93                "pattern{number:^width$}=> [{v}],\n               keys remainder    : {k}\n               targets remainder : {t}\n",
94                number = i + 1,
95                width = 4,
96                v = t.join("\n               "),
97                k = r.keys_remainder.iter().map(|k| k.to_string()).collect::<Vec<String>>().join(", "),
98                t = r.targets_remainder.iter().map(|k| k.to_string()).collect::<Vec<String>>().join(", "),
99            ))
100        }
101        s.join("\n")
102    }
103
104    /// Finds subsets sum of a target value. It can accept negative values.
105    ///
106    /// # Arguments
107    /// * `arr` - An array.
108    /// * `value` - The value to the sum of the subset comes.
109    /// * `max_length` - The maximum length of combinations of the answer.
110    /// # Example
111    /// ```
112    ///
113    /// use dpss::dp::find_subset;
114    /// let arr = vec![-1, -3, -2, 6, 12, 48];
115    /// let result = find_subset(arr, 0, 4);
116    /// let route1: Vec<i32> = vec![-3, -2, -1, 6];
117    /// let answer: Vec<Vec<i32>> = vec![route1];
118    /// assert_eq!(result, answer);
119    /// ```
120    ///
121    /// # Return Value
122    /// ```
123    ///
124    /// use dpss::dp::find_subset;
125    /// let result = find_subset(vec![1, 2, 3, -4, 5], 1, 2);
126    /// println!("{:?}", result);
127    /// ```
128    /// output: `[[1], [-3, 4]]`
129    pub fn find_subset(arr: Vec<i32>, value: i32, max_length: usize) -> Vec<Vec<i32>> {
130        _find_subset(&arr, value, max_length, None, None, None)
131    }
132
133    fn _find_subset(
134        arr: &Vec<i32>,
135        value: i32,
136        max_length: usize,
137        dptable: Option<&DpTable>,
138        arr_pos: Option<&Vec<u32>>,
139        offset: Option<i32>,
140    ) -> Vec<Vec<i32>> {
141        use std::cmp::max;
142        use std::cmp::min;
143        // https://stackoverflow.com/questions/43078142/subset-sum-with-negative-values-in-c-or-c
144        // Find a subset even if an array contains negative values.
145        let offset: i32 = match offset {
146            Some(x) => x,
147            None => {
148                (max(arr.iter().min().unwrap().abs() + 1, min(value, 0).abs() + 1)) as i32
149            }
150        };
151        let answer: Arc<RwLock<Vec<Vec<i32>>>> = Arc::new(RwLock::new(vec![]));
152        if offset == 0 && arr.iter().min().unwrap() >= &0 && value >= 0 {
153            let arr_pos = arr.iter().map(|e| *e as u32).collect::<Vec<u32>>();
154            let _dp: DpTable;
155            let dptable = match dptable {
156                Some(x) => x,
157                None => {
158                    _dp = _make_dp_table(&arr_pos, value as usize);
159                    &_dp
160                }
161            };
162            let result =
163                _find_subsetsfast_only_positive(&arr_pos, value as usize, max_length, dptable);
164            result.iter().for_each(|i| {
165                answer
166                    .write()
167                    .unwrap()
168                    .push(i.iter().map(|e| *e as i32).collect::<Vec<i32>>())
169            });
170            return vector_sorter(answer.read().unwrap().to_vec());
171        } else {
172            let length = arr.len();
173
174            // We will transform the array into a new array whose elements are all positive.
175            // And check if the transformed sum of the result of the new array is equal to the target value.
176            // If we find the sum is the same as the target, we will return the result.
177            let max_value = value + min(length, max_length) as i32 * offset;
178            let _arr_pos: &Vec<u32>;
179            let temp;
180            _arr_pos = match arr_pos {
181                None => {
182                    temp = arr
183                        .iter()
184                        .map(|e| (e + offset) as u32)
185                        .collect::<Vec<u32>>();
186                    &temp
187                }
188                Some(x) => x,
189            };
190            let temp2;
191            let dptable = match dptable {
192                Some(x) => x,
193                None => {
194                    temp2 = _make_dp_table(&_arr_pos, max_value as usize);
195                    &temp2
196                }
197            };
198            let c = |i| {
199                let result = _find_subsetsfast_only_positive(
200                    &_arr_pos,
201                    (value + (i as i32 * offset)) as usize,
202                    max_length,
203                    dptable,
204                );
205                result.iter().for_each(|res| {
206                    let mut tempsum: i32 = 0;
207                    let mut new_res: Vec<i32> = Vec::with_capacity(res.len());
208                    for j in res {
209                        let v = *j as i32 - offset;
210                        tempsum += v;
211                        new_res.push(v);
212                    }
213                    if tempsum == value {
214                        answer.write().unwrap().push(new_res);
215                    }
216                })
217            };
218            if cfg!(feature = "wasm") {
219                (1..min(length, max_length) + 1).into_iter().for_each(c);
220            } else {
221                (1..min(length, max_length) + 1).into_par_iter().for_each(c);
222            }
223            return vector_sorter(answer.read().unwrap().to_vec());
224        };
225    }
226
227    fn rec(
228        dp: &Vec<bool>,
229        arr: &Vec<u32>,
230        i: usize,
231        j: usize,
232        route: &mut Vec<u32>,
233        answer: &mut Vec<Vec<u32>>,
234        max_length: usize,
235        collen: usize,
236    ) {
237        // This code is mostly copied from https://drken1215.hatenablog.com/entry/2019/12/17/190300
238        // We follow the dp table backward to find combinations of subsets.
239        // We call this function recursively twice and this means the call stack expands like a tree.
240        if i == 0 {
241            if j == 0 {
242                // Only if we reach the root of the dp table, we choose the combination as an answer.
243                if route.len() <= max_length {
244                    answer.push(route.clone());
245                }
246            }
247            return;
248        }
249
250        if route.len() > max_length {
251            return;
252        }
253        let i_minus_one = i - 1;
254        let one_step_up = i_minus_one * collen + j;
255        let v = { *arr.get(i_minus_one).unwrap() };
256
257        if *dp.get(one_step_up).unwrap() == true {
258            rec(dp, arr, i_minus_one, j, route, answer, max_length, collen);
259        }
260
261        let j_v: usize = match j.checked_sub(v as usize) {
262            Some(x) => x,
263            None => return,
264        };
265        match dp.get(one_step_up - v as usize) {
266            Some(x) => {
267                if x == &true {
268                    route.push(v);
269                    rec(dp, arr, i_minus_one, j_v, route, answer, max_length, collen);
270                    route.pop();
271                }
272            }
273            None => (),
274        }
275    }
276
277    #[test]
278
279    fn test_vector_sorter() {
280        for _i in 0..1 {
281            let v = vec![vec![1, 3, 4], vec![4, 5]];
282            let r = vector_sorter(v);
283            assert_eq!(r, vec![vec![4, 5], vec![1, 3, 4]]);
284
285            let v = vec![vec![4, 2, 1], vec![4, 2]];
286            let r = vector_sorter(v);
287            assert_eq!(r, vec![vec![2, 4], vec![1, 2, 4]]);
288
289            let v = vec![vec![3, 0], vec![3], vec![2, 1], vec![1, 0, 2]];
290            let r = vector_sorter(v);
291            assert_eq!(r, vec![vec![3], vec![1, 2], vec![0, 3], vec![0, 1, 2]]);
292        }
293    }
294
295    fn vector_sorter<T: std::cmp::Ord + std::iter::Sum + std::clone::Clone + Copy>(
296        mut vec: Vec<Vec<T>>,
297    ) -> Vec<Vec<T>> {
298        if vec.len() == 0 {
299            return vec;
300        }
301        vec.sort_unstable();
302        vec.sort_unstable_by_key(|x| x.len());
303        vec.iter_mut().for_each(|x| x.sort_unstable());
304        vec
305    }
306
307    fn _make_dp_table(arr: &Vec<u32>, value: usize) -> DpTable {
308        let collen = value + 1;
309        let mut dp: Vec<bool> = vec![false; (value + 1) * (arr.len() + 1)];
310        dp[0] = true;
311        let mut current_address = 0;
312        arr.iter().for_each(|v_u32| {
313            let v_usize = *v_u32 as usize;
314            (0..value + 1).for_each(|_j| {
315                let current_value = *dp.get(current_address).unwrap();
316                if current_value == false {
317                    current_address += 1;
318                    return;
319                };
320                let address_onestep_down = current_address + collen;
321                dp[address_onestep_down] = true;
322
323                match dp.get_mut(address_onestep_down + v_usize) {
324                    Some(x) => {
325                        *x = true;
326                    }
327                    None => {}
328                }
329                current_address += 1;
330            });
331        });
332        DpTable {
333            dp: dp,
334            max_value: value,
335        }
336    }
337
338    fn _find_subsetsfast_only_positive(
339        arr: &Vec<u32>,
340        value: usize,
341        max_length: usize,
342        dptable: &DpTable,
343    ) -> Vec<Vec<u32>> {
344        // dp is a table that stores the information of subset sum.
345        // dp[i][j] is the number of ways to make sum j with i element.
346        // We follow from the start of this table.
347        // let mut dp: Vec<Vec<i32>> = vec![vec![0; value + 1]; arr.len() + 1];
348        let answer_exist: bool = *dptable
349            .dp
350            .get(dptable.dp.len() - 1 - (dptable.max_value - value))
351            .unwrap();
352        if answer_exist == false {
353            return vec![];
354        }
355        let collen = dptable.max_value + 1;
356        let a_length: usize = arr.len();
357        let mut route: Vec<u32> = vec![];
358        let mut answer: Vec<Vec<u32>> = vec![];
359        rec(
360            &dptable.dp,
361            &arr,
362            a_length,
363            value,
364            &mut route,
365            &mut answer,
366            max_length,
367            collen,
368        );
369        answer
370    }
371
372    fn vec_remove(arr: &mut Vec<i32>, v: i32) {
373        let index = arr.binary_search(&v).unwrap();
374        arr.remove(index);
375    }
376
377    /// Finds the integers from two vectors that sum to the same value.
378    /// This method assumes that the two vectors have Many-to-Many relationships.
379    /// Each integer of the `keys` vector corresponds to the multiple integers of the `targets` vector.
380    /// With this method, we can find combinations of the integers.
381    ///
382    /// To avoid combinatorial explosion, some parameters need to be set.
383    /// `max_key_length` is used to restrict the number of values in keys chosen.
384    /// If `max_key_length` is 3, an answer's length is at most 3, such as `[1980 + 2980 + 3500], [1050]`
385    /// `max_target_length` is the same as `max_key_length` for targets.
386    /// `n_candidates` specifies the maximum number of pattern.
387    /// If `use_all_keys` is true, an answer must contain all the elements of the keys.
388    /// If `use_all_targets` is true, an answer must contain all the elements of the targets.
389    /// When both `use_all_keys` and `use_all_targets` are true, the sum of the keys and the targets must be the same.
390    ///
391    /// # Arguments
392    /// * `keys` - An array.
393    /// * `targets` - An array.
394    /// * `max_key_length` - An integer.
395    /// * `max_target_length` - An integer.
396    /// * `n_candidates` - An integer.
397    /// * `use_all_keys` - Boolean.
398    /// * `use_all_targets` - Boolean.
399    /// # Example
400    ///
401    /// ```rust
402    ///
403    ///use dpss::dp::sequence_matcher;
404    ///let answer = sequence_matcher(&mut vec![1980, 2980, 3500, 4000, 1050], &mut vec![1950, 2900, 30, 80, 3300, 200, 3980, 1050, 20], 10, 10, 100, true, true).unwrap();
405    ///assert_eq!(answer[0].answer_arr, vec![
406    ///    (vec![1050],
407    ///     vec![1050]),
408    ///
409    ///     (vec![1980],
410    ///     vec![30, 1950]),
411    ///
412    ///     (vec![2980],
413    ///     vec![80, 2900]),
414    ///
415    ///     (vec![3500],
416    ///     vec![200, 3300]),
417    ///
418    ///     (vec![4000],
419    ///     vec![20, 3980]),
420    ///
421    ///    ]);
422    ///assert_eq!(answer[1].answer_arr, vec![
423    ///    (vec![1050],
424    ///     vec![1050]),
425    ///
426    ///     (vec![1980],
427    ///     vec![30, 1950]),
428    ///
429    ///     (vec![2980],
430    ///     vec![80, 2900]),
431    ///
432    ///     (vec![3500, 4000],
433    ///     vec![20, 200, 3300, 3980]),
434    ///
435    ///    ]);
436    /// ```
437    pub fn sequence_matcher(
438        keys: &mut Vec<i32>,
439        targets: &mut Vec<i32>,
440        max_key_length: usize,
441        max_target_length: usize,
442        n_candidates: usize,
443        use_all_keys: bool,
444        use_all_targets: bool,
445    ) -> Result<Vec<AnswerElement>, String> {
446        let mut group: Vec<(Vec<i32>, Vec<i32>)> = vec![];
447        let mut answer: Arc<RwLock<Vec<AnswerElement>>> = Arc::new(RwLock::new(vec![]));
448        if use_all_keys && use_all_targets {
449            let ks = keys.iter().sum::<i32>();
450            let ts = targets.iter().sum::<i32>();
451            if ks != ts {
452                return Err(format!("The sums of two arrays must be the same values. key's sum is {}. target's sum is {}. The difference is {}.", ks, ts, ks - ts));
453            }
454        }
455        let mut hashmap_fs: Arc<RwLock<HashMap<(Vec<i32>, i32), Vec<Vec<i32>>>>> =
456            Arc::new(RwLock::new(HashMap::new()));
457        keys.sort_unstable();
458        targets.sort_unstable();
459        let swap: bool;
460        let (keys, targets, max_key_length, max_target_length, use_all_keys, use_all_targets) =
461            if keys.len() > targets.len() {
462                swap = true;
463                (
464                    targets,
465                    keys,
466                    max_target_length,
467                    max_key_length,
468                    use_all_targets,
469                    use_all_keys,
470                )
471            } else {
472                swap = false;
473                (
474                    keys,
475                    targets,
476                    max_key_length,
477                    max_target_length,
478                    use_all_keys,
479                    use_all_targets,
480                )
481            };
482        use std::cmp::min;
483        (0..min(keys.len(), targets.len())).for_each(|i| {
484            sequence_matcher_core(
485                keys,
486                targets,
487                &mut group,
488                &mut answer,
489                max_key_length,
490                max_target_length,
491                &mut hashmap_fs,
492                n_candidates,
493                use_all_keys,
494                use_all_targets,
495                i,
496                vec![],
497            )
498        });
499        let mut answer_vec: Vec<AnswerElement> = answer.read().unwrap().to_vec();
500        if swap {
501            answer_vec.iter_mut().for_each(|x| {
502                x.answer_arr.iter_mut().for_each(|y| {
503                    std::mem::swap(&mut y.0, &mut y.1);
504                });
505                match x.swap(&"keys_remainder".to_string(), &"targets_remainder".to_string()) {
506                    Ok(_) => {},
507                    Err(e) => {
508                        panic!("{}", e);
509                    }
510                }
511            });
512        }
513        for i in 0..answer_vec.len() {
514            answer_vec[i]
515                .answer_arr
516                .sort_unstable_by_key(|k| k.0.iter().sum::<i32>());
517            answer_vec[i].answer_arr.sort_unstable_by_key(|k| k.0.len());
518        }
519        answer_vec.sort_unstable();
520        answer_vec.dedup();
521        if answer_vec.len() == 0 {
522            println!("Can't find any combination.");
523        }
524        Ok(answer_vec[..min(n_candidates, answer_vec.len())].to_vec())
525    }
526
527    fn sequence_matcher_core(
528        keys: &mut Vec<i32>,
529        targets: &mut Vec<i32>,
530        group: &mut Vec<(Vec<i32>, Vec<i32>)>,
531        answer: &mut Arc<RwLock<Vec<AnswerElement>>>,
532        max_key_length: usize,
533        max_target_length: usize,
534        hashmap_fs: &mut Arc<RwLock<HashMap<(Vec<i32>, i32), Vec<Vec<i32>>>>>,
535        n_candidates: usize,
536        use_all_keys: bool,
537        use_all_targets: bool,
538        max_depth: usize,
539        last_key: Vec<i32>,
540    ) -> () {
541        use itertools::Itertools;
542        use std::cmp::max;
543        use std::cmp::min;
544
545        if answer.read().unwrap().len() >= n_candidates {
546            return;
547        }
548
549        let add: bool = match (use_all_keys, use_all_targets) {
550            (true, true) => {
551                let add = match (keys.len() == 0, targets.len() == 0) {
552                    (true, true) => true,
553                    _ => false,
554                };
555                add
556            }
557            (true, false) => {
558                let add = match (keys.len() == 0, targets.len() == 0) {
559                    (true, true) => true,
560                    (true, false) => true,
561                    _ => false,
562                };
563                add
564            }
565            (false, true) => {
566                let add = match (keys.len() == 0, targets.len() == 0) {
567                    (true, true) => true,
568                    (false, true) => true,
569                    _ => false,
570                };
571                add
572            }
573            (false, false) => {
574                let add = match (keys.len() == 0, targets.len() == 0) {
575                    (true, true) => true,
576                    (false, true) => true,
577                    (true, false) => true,
578                    _ => false,
579                };
580                add
581            }
582        };
583
584        if add {
585            group.sort_unstable_by_key(|k| k.0.iter().sum::<i32>());
586            group.sort_unstable_by_key(|k| k.0.len());
587            let elem = AnswerElement {
588                answer_arr: group.clone(),
589                keys_remainder: keys.clone(),
590                targets_remainder: targets.clone(),
591            };
592            if answer.read().unwrap().contains(&elem) {
593                return;
594            } else {
595                answer.write().unwrap().push(elem.clone());
596                return;
597            }
598        }
599        if keys.len() == 0 || targets.len() == 0 {
600            return;
601        }
602        if group.len() > max_depth {
603            return;
604        }
605        targets.sort_unstable();
606        keys.sort_unstable();
607        keys.reverse();
608        let dp: DpTable;
609        let mut offset: i32 = 0;
610        let arr_pos: Vec<u32>;
611        let dp2: Option<&DpTable> =
612            if targets.iter().min().unwrap() >= &0 && keys.iter().min().unwrap() >= &0 {
613                arr_pos = targets.iter().map(|e| *e as u32).collect::<Vec<u32>>();
614                let max_value = keys[..min(max_key_length, keys.len())].iter().sum::<i32>();
615                dp = _make_dp_table(&arr_pos, max_value as usize);
616                Some(&dp)
617            } else {
618                offset = max(
619                    targets.iter().min().unwrap().abs() + 1,
620                    keys.iter().fold(0, |sum, x| min(sum, x + sum)).abs() + 1,
621                );
622                arr_pos = targets
623                    .iter()
624                    .map(|e| (e + offset) as u32)
625                    .collect::<Vec<u32>>();
626                let _max_value = keys[..min(max_key_length, keys.len())]
627                    .iter()
628                    .map(|x| max(0, *x))
629                    .sum::<i32>();
630                let max_value = _max_value + min(targets.len(), max_target_length) as i32 * offset;
631                dp = _make_dp_table(&arr_pos, max_value as usize);
632                Some(&dp)
633            };
634        keys.reverse();
635        let mut combs = vec![];
636        for i in 1..min(max_key_length, keys.len()) + 1 {
637            combs.push(keys.clone().into_iter().enumerate().combinations(i))
638        }
639        let mc = MultiCombination { combs: combs };
640        if cfg!(feature = "wasm") {
641            mc.for_each(|i| {
642                let sum_key: i32 = i.iter().map(|j| j.1).sum();
643                if sum_key < last_key.iter().sum() && i.len() == last_key.len() {
644                    return;
645                }
646                let mut sets = {
647                    match hashmap_fs.try_write() {
648                        Ok(mut v) => v
649                            .entry((targets.clone(), sum_key))
650                            .or_insert(_find_subset(
651                                &targets,
652                                sum_key,
653                                max_target_length,
654                                dp2,
655                                Some(&arr_pos),
656                                Some(offset),
657                            ))
658                            .clone(),
659                        Err(_) => _find_subset(
660                            &targets,
661                            sum_key,
662                            max_target_length,
663                            dp2,
664                            Some(&arr_pos),
665                            Some(offset),
666                        ),
667                    }
668                };
669                if sets.len() == 0 {
670                    return;
671                }
672                sets.dedup();
673                let mut keys_removed: Vec<i32> = keys.clone();
674                let vec_key: Vec<i32> = i
675                    .iter()
676                    .enumerate()
677                    .map(|(j2, j)| keys_removed.remove(j.0 - j2))
678                    .collect();
679                sets.iter().for_each(|set| {
680                    if set.len() == 0 {
681                        return;
682                    }
683                    let mut keys_for_next = keys_removed.clone();
684                    let mut targets_for_next = targets.clone();
685                    let mut group_for_next = group.clone();
686                    group_for_next.push((vec_key.clone(), set.clone()));
687                    set.iter().for_each(|j| {
688                        vec_remove(&mut targets_for_next, *j);
689                    });
690                    sequence_matcher_core(
691                        &mut keys_for_next,
692                        &mut targets_for_next,
693                        &mut group_for_next,
694                        &mut answer.clone(),
695                        max_key_length,
696                        max_target_length,
697                        &mut hashmap_fs.clone(),
698                        n_candidates,
699                        use_all_keys,
700                        use_all_targets,
701                        max_depth,
702                        vec_key.clone(),
703                    );
704                });
705            });
706        } else {
707            mc.par_bridge().for_each(|i| {
708                let sum_key: i32 = i.par_iter().map(|j| j.1).sum();
709                if sum_key < last_key.iter().sum() && i.len() == last_key.len() {
710                    return;
711                }
712                let mut sets = {
713                    match hashmap_fs.try_write() {
714                        Ok(mut v) => v
715                            .entry((targets.clone(), sum_key))
716                            .or_insert(_find_subset(
717                                &targets,
718                                sum_key,
719                                max_target_length,
720                                dp2,
721                                Some(&arr_pos),
722                                Some(offset),
723                            ))
724                            .clone(),
725                        Err(_) => _find_subset(
726                            &targets,
727                            sum_key,
728                            max_target_length,
729                            dp2,
730                            Some(&arr_pos),
731                            Some(offset),
732                        ),
733                    }
734                };
735                if sets.len() == 0 {
736                    return;
737                }
738                sets.dedup();
739                let mut keys_removed: Vec<i32> = keys.clone();
740                let vec_key: Vec<i32> = i
741                    .iter()
742                    .enumerate()
743                    .map(|(j2, j)| keys_removed.remove(j.0 - j2))
744                    .collect();
745                sets.par_iter().for_each(|set| {
746                    if set.len() == 0 {
747                        return;
748                    }
749                    let mut keys_for_next = keys_removed.clone();
750                    let mut targets_for_next = targets.clone();
751                    let mut group_for_next = group.clone();
752                    group_for_next.push((vec_key.clone(), set.clone()));
753                    set.iter().for_each(|j| {
754                        vec_remove(&mut targets_for_next, *j);
755                    });
756                    sequence_matcher_core(
757                        &mut keys_for_next,
758                        &mut targets_for_next,
759                        &mut group_for_next,
760                        &mut answer.clone(),
761                        max_key_length,
762                        max_target_length,
763                        &mut hashmap_fs.clone(),
764                        n_candidates,
765                        use_all_keys,
766                        use_all_targets,
767                        max_depth,
768                        vec_key.clone(),
769                    );
770                });
771            });
772        }
773        if use_all_keys == false && use_all_targets == false {
774            if group.len() == 0 {
775                return;
776            }
777            let elem = AnswerElement {
778                answer_arr: group.clone(),
779                keys_remainder: keys.clone(),
780                targets_remainder: targets.clone(),
781            };
782            answer.write().unwrap().push(elem.clone());
783        }
784        ()
785    }
786
787    #[test]
788    fn test_sequence_matcher() {
789        let answer = sequence_matcher(
790            &mut vec![-950, 10000],
791            &mut vec![5000, 4000, 50],
792            10,
793            10,
794            2,
795            true,
796            true,
797        )
798        .unwrap();
799        assert_eq!(
800            answer[0].answer_arr,
801            vec![(vec![-950, 10000], vec![50, 4000, 5000]),]
802        );
803
804        let answer = sequence_matcher(
805            &mut vec![6, 7, 3, 2, -9, -3, 8, 3, 6, -10],
806            &mut vec![3, 2, -6, -8, 2, -9, 0, -5, -3, 37],
807            7,
808            6,
809            30,
810            true,
811            true,
812        )
813        .unwrap();
814        assert!(answer.len() >= 29 && answer.len() <= 31);
815        // Sometimes the answer is 29 or 31, It may be due to parallel execution. Currently I ignore it.
816
817        let answer = sequence_matcher(
818            &mut vec![100, 200, 300, 400, 500, 600, -700, 800, 900, 1000],
819            &mut vec![300, 700, 500, 600, -700, 2700],
820            3,
821            2,
822            200,
823            true,
824            true,
825        )
826        .unwrap();
827        assert_eq!(answer.len(), 195);
828        assert_eq!(
829            answer[0].answer_arr,
830            vec![
831                (vec![-700], vec![-700]),
832                (vec![100, 200], vec![300]),
833                (vec![300, 400], vec![700]),
834                (vec![500, 600], vec![500, 600]),
835                (vec![800, 900, 1000], vec![2700]),
836            ]
837        );
838
839        let answer = sequence_matcher(
840            &mut vec![9, 0, 1, 7, 1],
841            &mut vec![7, 2, 8, 0, 1],
842            3,
843            2,
844            100,
845            true,
846            true,
847        )
848        .unwrap();
849        assert_eq!(answer.len(), 24);
850        assert_eq!(
851            answer[0].answer_arr,
852            vec![
853                (vec![0], vec![0]),
854                (vec![1], vec![1]),
855                (vec![7], vec![7]),
856                (vec![1, 9], vec![2, 8]),
857            ]
858        );
859
860        let answer = sequence_matcher(
861            &mut vec![1000, 1100, 150, 123, 5, 10],
862            &mut vec![2100, 273, 4, 11],
863            6,
864            4,
865            200,
866            true,
867            true,
868        )
869        .unwrap();
870        assert_eq!(answer.len(), 5);
871        assert_eq!(
872            answer[0].answer_arr,
873            vec![
874                (vec![5, 10], vec![4, 11]),
875                (vec![123, 150], vec![273]),
876                (vec![1000, 1100], vec![2100]),
877            ]
878        );
879        assert_eq!(
880            answer[2].answer_arr,
881            vec![(vec![5, 10, 123, 150, 1000, 1100], vec![4, 11, 273, 2100]),]
882        );
883
884        let answer = sequence_matcher(
885            &mut vec![1, 2, 3],
886            &mut vec![1000, 1200],
887            10,
888            10,
889            2,
890            true,
891            true,
892        );
893        let expected = Err(format!("The sums of two arrays must be the same values. key's sum is {}. target's sum is {}. The difference is {}.", 6, 2200, -2194));
894        assert_eq!(answer, expected);
895
896        let answer = sequence_matcher(
897            &mut vec![1, 2, 3, 4],
898            &mut vec![1, 5],
899            10,
900            10,
901            2,
902            true,
903            true,
904        );
905        let expected = Err(format!("The sums of two arrays must be the same values. key's sum is {}. target's sum is {}. The difference is {}.", 10, 6, 4));
906
907        assert_eq!(answer, expected);
908
909        let answer = sequence_matcher(
910            &mut vec![183, 36, 231, 128, 137],
911            &mut vec![8, 9, 15, 15, 33, 36, 39, 45, 46, 60, 68, 73, 80, 92, 96],
912            1,
913            15,
914            20,
915            true,
916            true,
917        )
918        .unwrap();
919
920        assert_eq!(answer.len(), 13);
921        assert_eq!(
922            answer[0].answer_arr,
923            vec![
924                (vec![36], vec![36]),
925                (vec![128], vec![9, 39, 80]),
926                (vec![137], vec![8, 33, 96]),
927                (vec![183], vec![45, 46, 92]),
928                (vec![231], vec![15, 15, 60, 68, 73]),
929            ]
930        );
931    }
932    #[test]
933
934    fn test_sequence_matcher_allowing_imcomplete_answer() {
935        let answer = sequence_matcher(
936            &mut vec![1, 2, -3, 4, 5],
937            &mut vec![1, 2],
938            6,
939            4,
940            200,
941            true,
942            false,
943        )
944        .unwrap();
945        assert_eq!(answer.len(), 0);
946
947        let answer = sequence_matcher(
948            &mut vec![1, 2, -3, 4, 5],
949            &mut vec![1, 2],
950            6,
951            4,
952            200,
953            false,
954            true,
955        )
956        .unwrap();
957        assert_eq!(answer.len(), 6);
958        assert_eq!(answer[0].answer_arr, vec![(vec![-3, 1, 5], vec![1, 2]),]);
959    }
960
961    #[test]
962    fn test_sequence_matcher_allowing_imcomplete_answer_complicated() {
963        let answer = sequence_matcher(
964            &mut vec![-755, 222, 851, 291, -511, -567, 958, 939, -28],
965            &mut vec![-590, 785, -597, -184, -968, -555, -221, -28],
966            30,
967            30,
968            200,
969            false,
970            true,
971        )
972        .unwrap();
973        assert_eq!(answer.len(), 0);
974
975        let answer = sequence_matcher(
976            &mut vec![-755, 222, 851, 291, -511, -567, 958, 939, -28],
977            &mut vec![-590, 785, -597, -184, -968, -555, -221, -28],
978            30,
979            30,
980            100,
981            false,
982            false,
983        )
984        .unwrap();
985        assert_eq!(
986            answer[0].answer_arr,
987            vec![(
988                vec![-755, -567, -511, -28, 939],
989                vec![-968, -555, -184, 785]
990            ),]
991        );
992    }
993}
994
995#[cfg(test)]
996mod tests {
997
998    use super::*;
999
1000    #[test]
1001    fn test_find_subset() {
1002        let result = dp::find_subset(vec![1, 2, 3], 3, 2);
1003        let route1: Vec<i32> = vec![3];
1004        let route2: Vec<i32> = vec![1, 2];
1005        let answer: Vec<Vec<i32>> = vec![route1, route2];
1006        assert_eq!(result, answer);
1007
1008        let result = dp::find_subset(vec![0, 3, 5, 10], 3, 2);
1009        let route1: Vec<i32> = vec![3];
1010        let route2: Vec<i32> = vec![0, 3];
1011        let answer: Vec<Vec<i32>> = vec![route1, route2];
1012        assert_eq!(result, answer);
1013
1014        let result = dp::find_subset(vec![1, 2, 3, 0], 3, 3);
1015        let route1: Vec<i32> = vec![3];
1016        let route2: Vec<i32> = vec![0, 3];
1017        let route3: Vec<i32> = vec![1, 2];
1018        let route4: Vec<i32> = vec![0, 1, 2];
1019        let answer: Vec<Vec<i32>> = vec![route1, route2, route3, route4];
1020        assert_eq!(result, answer);
1021
1022        let result = dp::find_subset(vec![1, 2, 3], 3, 2);
1023        let route1: Vec<i32> = vec![3];
1024        let route2: Vec<i32> = vec![1, 2];
1025        let answer: Vec<Vec<i32>> = vec![route1, route2];
1026        assert_eq!(result, answer);
1027
1028        let result = dp::find_subset(vec![1, 2, 3, 4, 5], 10, 4);
1029        let route1: Vec<i32> = vec![2, 3, 5];
1030        let route2: Vec<i32> = vec![1, 4, 5];
1031        let route3: Vec<i32> = vec![1, 2, 3, 4];
1032        let answer: Vec<Vec<i32>> = vec![route1, route2, route3];
1033        assert_eq!(result, answer);
1034
1035        let result = dp::find_subset(vec![1, 2, 3, 4, 5], 10, 3);
1036        let route2: Vec<i32> = vec![2, 3, 5];
1037        let route3: Vec<i32> = vec![1, 4, 5];
1038        let answer: Vec<Vec<i32>> = vec![route2, route3];
1039        assert_eq!(result, answer);
1040
1041        let arr = vec![75, 467, 512, -835, 770, -69, 10];
1042        let result = dp::find_subset(arr, 711, 3);
1043        let route1: Vec<i32> = vec![-69, 10, 770];
1044        let answer: Vec<Vec<i32>> = vec![route1];
1045        assert_eq!(result, answer);
1046
1047        let arr = vec![-3, 10, 56, -33, 65, -9, 8, 72, 63, 35];
1048        let result = dp::find_subset(arr, 7, 4);
1049        let route1: Vec<i32> = vec![-3, 10];
1050        let route2: Vec<i32> = vec![-33, -3, 8, 35];
1051        let answer: Vec<Vec<i32>> = vec![route1, route2];
1052        assert_eq!(result, answer);
1053
1054        let arr = vec![
1055            73209, 95597, 84735, 40496, 83553, 95595, -628, 201, 27597, 7904, 98445, 6241, 33002,
1056            -776, -711, 45552, 86746, 84248, 66278, 37475,
1057        ];
1058        let result = dp::find_subset(arr, 72782, 3);
1059        let route1: Vec<i32> = vec![-628, 201, 73209];
1060        let answer: Vec<Vec<i32>> = vec![route1];
1061        assert_eq!(result, answer);
1062
1063        let arr = vec![-1, 2, 3];
1064        let result = dp::find_subset(arr, -1, 1);
1065        let route1: Vec<i32> = vec![-1];
1066        let answer: Vec<Vec<i32>> = vec![route1];
1067        assert_eq!(result, answer);
1068
1069        let arr = vec![-10, 5, -2];
1070        let result = dp::find_subset(arr, -5, 2);
1071        let route1: Vec<i32> = vec![-10, 5];
1072        let answer: Vec<Vec<i32>> = vec![route1];
1073        assert_eq!(result, answer);
1074
1075        let arr = vec![-3, -5, -7];
1076        let result = dp::find_subset(arr, -15, 3);
1077        let route1: Vec<i32> = vec![-7, -5, -3];
1078        let answer: Vec<Vec<i32>> = vec![route1];
1079        assert_eq!(result, answer);
1080
1081        let arr = vec![-100, 10, 20];
1082        let result = dp::find_subset(arr, -70, 3);
1083        let route1: Vec<i32> = vec![-100, 10, 20];
1084        let answer: Vec<Vec<i32>> = vec![route1];
1085        assert_eq!(result, answer);
1086    }
1087}