//-
// Copyright 2017 Jason Lingle
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

//! Support for combining strategies into tuples.
//!
//! There is no explicit "tuple strategy"; simply make a tuple containing the
//! strategy and that tuple is itself a strategy.

use crate::strategy::*;
use crate::test_runner::*;

/// Common `ValueTree` implementation for all tuple strategies.
#[derive(Clone, Copy, Debug)]
pub struct TupleValueTree<T> {
    tree: T,
    shrinker: u32,
    prev_shrinker: Option<u32>,
}

impl<T> TupleValueTree<T> {
    /// Create a new `TupleValueTree` wrapping `inner`.
    ///
    /// It only makes sense for `inner` to be a tuple of an arity for which the
    /// type implements `ValueTree`.
    pub fn new(inner: T) -> Self {
        TupleValueTree {
            tree: inner,
            shrinker: 0,
            prev_shrinker: None,
        }
    }
}

macro_rules! tuple {
    ($($fld:tt : $typ:ident),*) => {
        impl<$($typ : Strategy),*> Strategy for ($($typ,)*) {
            type Tree = TupleValueTree<($($typ::Tree,)*)>;
            type Value = ($($typ::Value,)*);

            fn new_tree(&self, runner: &mut TestRunner) -> NewTree<Self> {
                let values = ($(self.$fld.new_tree(runner)?,)*);
                Ok(TupleValueTree::new(values))
            }
        }

        impl<$($typ : ValueTree),*> ValueTree
        for TupleValueTree<($($typ,)*)> {
            type Value = ($($typ::Value,)*);

            fn current(&self) -> Self::Value {
                ($(self.tree.$fld.current(),)*)
            }

            fn simplify(&mut self) -> bool {
                $(
                    if $fld == self.shrinker {
                        if self.tree.$fld.simplify() {
                            self.prev_shrinker = Some(self.shrinker);
                            return true;
                        } else {
                            self.shrinker += 1;
                        }
                    }
                )*
                false
            }

            fn complicate(&mut self) -> bool {
                if let Some(shrinker) = self.prev_shrinker {$(
                    if $fld == shrinker {
                        if self.tree.$fld.complicate() {
                            self.shrinker = shrinker;
                            return true;
                        } else {
                            self.prev_shrinker = None;
                            return false;
                        }
                    }
                )*}
                false
            }
        }
    }
}

tuple!(0: A);
tuple!(0: A, 1: B);
tuple!(0: A, 1: B, 2: C);
tuple!(0: A, 1: B, 2: C, 3: D);
tuple!(0: A, 1: B, 2: C, 3: D, 4: E);
tuple!(0: A, 1: B, 2: C, 3: D, 4: E, 5: F);
tuple!(0: A, 1: B, 2: C, 3: D, 4: E, 5: F, 6: G);
tuple!(0: A, 1: B, 2: C, 3: D, 4: E, 5: F, 6: G, 7: H);
tuple!(0: A, 1: B, 2: C, 3: D, 4: E, 5: F, 6: G, 7: H, 8: I);
tuple!(0: A, 1: B, 2: C, 3: D, 4: E, 5: F, 6: G, 7: H, 8: I, 9: J);

#[cfg(test)]
mod test {
    use crate::strategy::*;

    use super::*;

    #[test]
    fn shrinks_fully_ltr() {
        fn pass(a: (i32, i32)) -> bool {
            a.0 * a.1 <= 9
        }

        let input = (0..32, 0..32);
        let mut runner = TestRunner::default();

        let mut cases_tested = 0;
        for _ in 0..256 {
            // Find a failing test case
            let mut case = input.new_tree(&mut runner).unwrap();
            if pass(case.current()) { continue; }

            loop {
                if pass(case.current()) {
                    if !case.complicate() { break; }
                } else {
                    if !case.simplify() { break; }
                }
            }

            let last = case.current();
            assert!(!pass(last));
            // Maximally shrunken
            assert!(pass((last.0 - 1, last.1)));
            assert!(pass((last.0, last.1 - 1)));

            cases_tested += 1;
        }

        assert!(cases_tested > 32, "Didn't find enough test cases");
    }

    #[test]
    fn test_sanity() {
        check_strategy_sanity((0i32..100, 0i32..1000, 0i32..10000), None);
    }
}
