1use strict;
2use warnings;
3
4use Test::More tests => 517;
5
6use_ok('Math::Series');
7
8my @args = (
9    {
10        formula       => 'n*x',
11        start_value   => 1,
12        iteration_var => 'n',
13        previous_var  => 'x',
14        start_index   => 0,
15    },
16    {
17        formula     => 'n*x',
18        start_value => 1,
19    },
20    {
21        formula     => 'n*x',
22        start_value => 1,
23        start_index => 0,
24    },
25    {
26        formula       => 'n*x',
27        start_value   => 1,
28        iteration_var => 'n',
29        previous_var  => 'x',
30        start_index   => 4,
31    },
32    {
33        formula     => 'n*x',
34        start_value => 1,
35        start_index => 4,
36    },
37    {
38        formula       => 'n*x',
39        start_value   => 1,
40        iteration_var => 'n',
41        start_index   => 4,
42    },
43);
44
45foreach my $args (@args) {
46    my $ca = Math::Series->new(%$args);
47    my $cb = Math::Series->new( %$args, cached => 1 );
48    isa_ok( $ca, 'Math::Series' );
49    isa_ok( $cb, 'Math::Series' );
50
51    my $cn = Math::Series->new( %$args, cached => 0 );
52    isa_ok( $cn, 'Math::Series' );
53
54    ok( $ca->cached() == 1, 'sequence cached by default' );
55    ok( $cb->cached() == 1, 'sequence cached by default, as requested' );
56    ok( $cn->cached() == 0, 'sequence not cached, as requested' );
57
58    $ca->cached(0);
59    ok( $ca->cached() == 0, 'sequence not cached after change' );
60    $ca->cached(1);
61    ok( $ca->cached() == 1, 'sequence cached after change' );
62
63    my @range = map { $_ + $ca->{start_index} } ( 0 .. 7 );
64    my @results = $ca->{start_index} == 4
65      ? qw/
66      1
67      6
68      42
69      336
70      3024
71      30240
72      332640
73      3991680
74      51891840
75      726485760
76      10897286400
77      174356582400
78      /
79      : qw/
80      1
81      2
82      6
83      24
84      120
85      720
86      5040
87      40320
88      362880
89      3628800
90      39916800
91      479001600
92      /;
93
94    foreach (@range) {
95        ok( $ca->current_index() == $_,
96            'Testing current_index() of cached object.' );
97        ok( $cn->current_index() == $_,
98            'Testing current_index() of uncached object.' );
99        ok( $ca->next()->value() == $results[ $_ - $ca->{start_index} ],
100            'Testing next() of cached object.' );
101        ok( $cn->next()->value() == $results[ $_ - $ca->{start_index} ],
102            'Testing next() of uncached object.' );
103    }
104
105    $Math::Series::warnings = $Math::Series::warnings = 0;
106    foreach ( reverse @range ) {
107        ok( $ca->back()->value() == $results[ $_ - $ca->{start_index} ],
108            'Testing back() of cached object.' );
109        ok( $cn->back()->value() == $results[ $_ - $ca->{start_index} ],
110            'Testing back() of uncached object.' );
111        ok( $ca->current_index() == $_,
112            'Testing current_index() of cached object after back().' );
113        ok( $cn->current_index() == $_,
114            'Testing current_index() of uncached object after back().' );
115    }
116
117    ok(
118        $ca->current_index( 5 + $ca->{start_index} ) == 5 + $ca->{start_index},
119        'Testing setting current_index() on cached object.'
120    );
121    ok(
122        $cn->current_index( 5 + $ca->{start_index} ) == 5 + $ca->{start_index},
123        'Testing setting current_index() on uncached object.'
124    );
125
126    ok(
127        $ca->at_index( 4 + $ca->{start_index} )->value() == $results[4],
128        'Testing at_index() (below current index) on cached object.'
129    );
130    ok(
131        $cn->at_index( 4 + $ca->{start_index} )->value() == $results[4],
132        'Testing at_index() (below current index) on uncached object.'
133    );
134
135    ok(
136        $ca->at_index( 6 + $ca->{start_index} )->value() == $results[6],
137        'Testing at_index() (above cur. index but cached) on cached object.'
138    );
139    ok(
140        $cn->at_index( 6 + $ca->{start_index} )->value() == $results[6],
141        'Testing at_index() (above cur. index) on uncached object.'
142    );
143
144    ok(
145        $ca->at_index( 9 + $ca->{start_index} )->value() == $results[9],
146        'Testing at_index() (above current index) on cached object.'
147    );
148    ok(
149        $cn->at_index( 9 + $ca->{start_index} )->value() == $results[9],
150        'Testing at_index() (above current index) on uncached object.'
151    );
152
153    ok(
154        !defined( $ca->at_index( -1 + $ca->{start_index} ) ),
155        'Testing at_index() with invalid index on cached object.'
156    );
157    ok(
158        !defined( $cn->at_index( -1 + $ca->{start_index} ) ),
159        'Testing at_index() with invalid index on uncached object.'
160    );
161
162    my $c = $ca->current_index( $ca->{start_index} - 1 );
163    ok(
164        !defined( $ca->current_index( $ca->{start_index} - 1 ) ),
165        'Testing current_index() with invalid index on cached object.'
166    );
167    ok(
168        !defined( $cn->current_index( $cn->{start_index} - 1 ) ),
169        'Testing current_index() with invalid index on uncached object.'
170    );
171
172    $ca->current_index( $ca->{start_index} );
173    $cn->current_index( $cn->{start_index} );
174
175    ok( !defined( $ca->back() ),
176        'Testing back() with invalid index on cached object.' );
177    ok( !defined( $cn->back() ),
178        'Testing back() with invalid index on uncached object.' );
179}
180