line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
package Date::Manip::Delta; |
2
|
|
|
|
|
|
|
# Copyright (c) 1995-2023 Sullivan Beck. All rights reserved. |
3
|
|
|
|
|
|
|
# This program is free software; you can redistribute it and/or modify it |
4
|
|
|
|
|
|
|
# under the same terms as Perl itself. |
5
|
|
|
|
|
|
|
|
6
|
|
|
|
|
|
|
######################################################################## |
7
|
|
|
|
|
|
|
# Any routine that starts with an underscore (_) is NOT intended for |
8
|
|
|
|
|
|
|
# public use. They are for internal use in the the Date::Manip |
9
|
|
|
|
|
|
|
# modules and are subject to change without warning or notice. |
10
|
|
|
|
|
|
|
# |
11
|
|
|
|
|
|
|
# ABSOLUTELY NO USER SUPPORT IS OFFERED FOR THESE ROUTINES! |
12
|
|
|
|
|
|
|
######################################################################## |
13
|
|
|
|
|
|
|
|
14
|
168
|
|
|
168
|
|
1141
|
use Date::Manip::Obj; |
|
168
|
|
|
|
|
299
|
|
|
168
|
|
|
|
|
7663
|
|
15
|
|
|
|
|
|
|
@ISA = ('Date::Manip::Obj'); |
16
|
|
|
|
|
|
|
|
17
|
|
|
|
|
|
|
require 5.010000; |
18
|
168
|
|
|
168
|
|
881
|
use warnings; |
|
168
|
|
|
|
|
327
|
|
|
168
|
|
|
|
|
4602
|
|
19
|
168
|
|
|
168
|
|
765
|
use strict; |
|
168
|
|
|
|
|
295
|
|
|
168
|
|
|
|
|
3930
|
|
20
|
168
|
|
|
168
|
|
823
|
use utf8; |
|
168
|
|
|
|
|
283
|
|
|
168
|
|
|
|
|
1135
|
|
21
|
168
|
|
|
168
|
|
4131
|
use IO::File; |
|
168
|
|
|
|
|
334
|
|
|
168
|
|
|
|
|
26400
|
|
22
|
168
|
|
|
168
|
|
1030
|
use Carp; |
|
168
|
|
|
|
|
284
|
|
|
168
|
|
|
|
|
8795
|
|
23
|
|
|
|
|
|
|
#use re 'debug'; |
24
|
|
|
|
|
|
|
|
25
|
168
|
|
|
168
|
|
930
|
use Date::Manip::Base; |
|
168
|
|
|
|
|
287
|
|
|
168
|
|
|
|
|
4018
|
|
26
|
168
|
|
|
168
|
|
818
|
use Date::Manip::TZ; |
|
168
|
|
|
|
|
340
|
|
|
168
|
|
|
|
|
232016
|
|
27
|
|
|
|
|
|
|
|
28
|
|
|
|
|
|
|
our $VERSION; |
29
|
|
|
|
|
|
|
$VERSION='6.92'; |
30
|
168
|
|
|
168
|
|
846
|
END { undef $VERSION; } |
31
|
|
|
|
|
|
|
|
32
|
|
|
|
|
|
|
######################################################################## |
33
|
|
|
|
|
|
|
# BASE METHODS |
34
|
|
|
|
|
|
|
######################################################################## |
35
|
|
|
|
|
|
|
|
36
|
|
|
|
|
|
|
sub is_delta { |
37
|
1
|
|
|
1
|
1
|
160
|
return 1; |
38
|
|
|
|
|
|
|
} |
39
|
|
|
|
|
|
|
|
40
|
|
|
|
|
|
|
sub config { |
41
|
15
|
|
|
15
|
1
|
106
|
my($self,@args) = @_; |
42
|
15
|
|
|
|
|
137
|
$self->SUPER::config(@args); |
43
|
|
|
|
|
|
|
|
44
|
|
|
|
|
|
|
# A new config can change the value of the format fields, so clear them. |
45
|
15
|
|
|
|
|
53
|
$$self{'data'}{'f'} = {}; |
46
|
15
|
|
|
|
|
64
|
$$self{'data'}{'flen'} = {}; |
47
|
|
|
|
|
|
|
} |
48
|
|
|
|
|
|
|
|
49
|
|
|
|
|
|
|
# Call this every time a new delta is put in to make sure everything is |
50
|
|
|
|
|
|
|
# correctly initialized. |
51
|
|
|
|
|
|
|
# |
52
|
|
|
|
|
|
|
sub _init { |
53
|
12026
|
|
|
12026
|
|
17780
|
my($self) = @_; |
54
|
|
|
|
|
|
|
|
55
|
12026
|
|
|
|
|
22551
|
my $def = [0,0,0,0,0,0,0]; |
56
|
12026
|
|
|
|
|
17402
|
my $dmt = $$self{'tz'}; |
57
|
12026
|
|
|
|
|
15001
|
my $dmb = $$dmt{'base'}; |
58
|
|
|
|
|
|
|
|
59
|
12026
|
|
|
|
|
16013
|
$$self{'err'} = ''; |
60
|
12026
|
|
|
|
|
81388
|
$$self{'data'} = |
61
|
|
|
|
|
|
|
{ |
62
|
|
|
|
|
|
|
'delta' => $def, # the delta put in (all negative fields signed) |
63
|
|
|
|
|
|
|
|
64
|
|
|
|
|
|
|
'in' => '', # the string that was parsed (if any) |
65
|
|
|
|
|
|
|
'length' => 0, # length of delta (in seconds) |
66
|
|
|
|
|
|
|
|
67
|
|
|
|
|
|
|
'gotmode' => 0, # 1 if mode set explicitly |
68
|
|
|
|
|
|
|
'mode' => 'standard', # standard/business |
69
|
|
|
|
|
|
|
'type' => 'exact', # exact, semi, estimated, approx |
70
|
|
|
|
|
|
|
'type_from' => 'init', # where did the type come from |
71
|
|
|
|
|
|
|
# init - from here |
72
|
|
|
|
|
|
|
# opt - specified in an option/string |
73
|
|
|
|
|
|
|
# det - determined automatically |
74
|
|
|
|
|
|
|
'normalized' => 1, # 1 if normalized |
75
|
|
|
|
|
|
|
|
76
|
|
|
|
|
|
|
'f' => {}, # format fields |
77
|
|
|
|
|
|
|
'flen' => {}, # field lengths |
78
|
|
|
|
|
|
|
} |
79
|
|
|
|
|
|
|
} |
80
|
|
|
|
|
|
|
|
81
|
|
|
|
|
|
|
sub _init_args { |
82
|
2
|
|
|
2
|
|
5
|
my($self) = @_; |
83
|
|
|
|
|
|
|
|
84
|
2
|
|
|
|
|
4
|
my @args = @{ $$self{'args'} }; |
|
2
|
|
|
|
|
6
|
|
85
|
2
|
|
|
|
|
11
|
$self->parse(@args); |
86
|
|
|
|
|
|
|
} |
87
|
|
|
|
|
|
|
|
88
|
|
|
|
|
|
|
sub value { |
89
|
3422
|
|
|
3422
|
1
|
6522
|
my($self,$as_input) = @_; |
90
|
|
|
|
|
|
|
|
91
|
3422
|
50
|
|
|
|
6450
|
if ($$self{'err'}) { |
92
|
0
|
0
|
|
|
|
0
|
return () if (wantarray); |
93
|
0
|
|
|
|
|
0
|
return ''; |
94
|
|
|
|
|
|
|
} |
95
|
|
|
|
|
|
|
|
96
|
3422
|
|
|
|
|
4490
|
my $dmt = $$self{'tz'}; |
97
|
3422
|
|
|
|
|
4295
|
my $dmb = $$dmt{'base'}; |
98
|
|
|
|
|
|
|
|
99
|
3422
|
|
|
|
|
3975
|
my @delta = @{ $$self{'data'}{'delta'} }; |
|
3422
|
|
|
|
|
7994
|
|
100
|
|
|
|
|
|
|
|
101
|
3422
|
100
|
|
|
|
11349
|
return @delta if (wantarray); |
102
|
339
|
|
|
|
|
394
|
my $err; |
103
|
|
|
|
|
|
|
|
104
|
|
|
|
|
|
|
my %o = ( 'source' => 'delta', |
105
|
|
|
|
|
|
|
'nonorm' => 1, |
106
|
|
|
|
|
|
|
'type' => $$self{'data'}{'type'}, |
107
|
|
|
|
|
|
|
'sign' => 0, |
108
|
339
|
|
|
|
|
1104
|
'mode' => $$self{'data'}{'mode'}, |
109
|
|
|
|
|
|
|
); |
110
|
|
|
|
|
|
|
|
111
|
339
|
|
|
|
|
985
|
($err,@delta) = $dmb->_delta_fields( \%o, [@delta]); |
112
|
339
|
|
|
|
|
1994
|
return join(':',@delta); |
113
|
|
|
|
|
|
|
} |
114
|
|
|
|
|
|
|
|
115
|
|
|
|
|
|
|
sub input { |
116
|
0
|
|
|
0
|
1
|
0
|
my($self) = @_; |
117
|
0
|
|
|
|
|
0
|
return $$self{'data'}{'in'}; |
118
|
|
|
|
|
|
|
} |
119
|
|
|
|
|
|
|
|
120
|
|
|
|
|
|
|
######################################################################## |
121
|
|
|
|
|
|
|
# DELTA METHODS |
122
|
|
|
|
|
|
|
######################################################################## |
123
|
|
|
|
|
|
|
|
124
|
0
|
|
|
|
|
0
|
BEGIN { |
125
|
168
|
|
|
168
|
|
598788
|
my %f = qw( y 0 M 1 w 2 d 3 h 4 m 5 s 6 ); |
126
|
|
|
|
|
|
|
|
127
|
|
|
|
|
|
|
sub set { |
128
|
4988
|
|
|
4988
|
1
|
126513
|
my($self,@args) = @_; |
129
|
4988
|
|
|
|
|
6157
|
my %opts; |
130
|
4988
|
100
|
|
|
|
8939
|
if (ref($args[0]) eq 'HASH') { |
131
|
120
|
|
|
|
|
134
|
%opts = %{ $args[0] }; |
|
120
|
|
|
|
|
454
|
|
132
|
|
|
|
|
|
|
} else { |
133
|
|
|
|
|
|
|
# *** DEPRECATED 7.0 *** |
134
|
4868
|
100
|
|
|
|
8169
|
if (@args == 3) { |
135
|
15
|
50
|
|
|
|
43
|
%opts = ( $args[0] => $args[1], |
136
|
|
|
|
|
|
|
'nonorm' => ($args[2] ? 1 : 0) ); |
137
|
|
|
|
|
|
|
} else { |
138
|
4853
|
|
|
|
|
9128
|
%opts = ( $args[0] => $args[1] ); |
139
|
|
|
|
|
|
|
} |
140
|
|
|
|
|
|
|
} |
141
|
|
|
|
|
|
|
|
142
|
|
|
|
|
|
|
# Check for some invalid opts |
143
|
|
|
|
|
|
|
|
144
|
4988
|
|
|
|
|
11763
|
foreach my $key (keys %opts) { |
145
|
5163
|
|
|
|
|
7274
|
my $val = $opts{$key}; |
146
|
5163
|
|
|
|
|
7587
|
delete $opts{$key}; |
147
|
|
|
|
|
|
|
|
148
|
|
|
|
|
|
|
# *** DEPRECATED 7.0 *** |
149
|
5163
|
50
|
|
|
|
9846
|
$key = 'standard' if (lc($key) eq 'normal'); |
150
|
|
|
|
|
|
|
|
151
|
5163
|
100
|
100
|
|
|
14237
|
if (lc($key) eq 'delta' || |
|
|
100
|
100
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
|
100
|
|
|
|
|
152
|
|
|
|
|
|
|
lc($key) eq 'business' || |
153
|
|
|
|
|
|
|
lc($key) eq 'standard' || |
154
|
|
|
|
|
|
|
lc($key) eq 'nonorm' || |
155
|
|
|
|
|
|
|
lc($key) eq 'mode' || |
156
|
|
|
|
|
|
|
lc($key) eq 'type') { |
157
|
|
|
|
|
|
|
|
158
|
5153
|
100
|
|
|
|
9932
|
if (exists $opts{lc($key)}) { |
159
|
1
|
|
|
|
|
2
|
$key = lc($key); |
160
|
1
|
|
|
|
|
6
|
$$self{'err'} = "[set] Invalid option: $key entered twice"; |
161
|
1
|
|
|
|
|
5
|
return 1; |
162
|
|
|
|
|
|
|
} |
163
|
|
|
|
|
|
|
|
164
|
5152
|
|
|
|
|
10261
|
$opts{lc($key)} = $val; |
165
|
|
|
|
|
|
|
|
166
|
|
|
|
|
|
|
} elsif ($key =~ /^[yMwdhms]$/) { |
167
|
|
|
|
|
|
|
|
168
|
9
|
|
|
|
|
24
|
$opts{$key} = $val; |
169
|
|
|
|
|
|
|
|
170
|
|
|
|
|
|
|
} else { |
171
|
1
|
|
|
|
|
4
|
$$self{'err'} = "[set] Unknown option: $key"; |
172
|
1
|
|
|
|
|
3
|
return 1; |
173
|
|
|
|
|
|
|
} |
174
|
|
|
|
|
|
|
} |
175
|
|
|
|
|
|
|
|
176
|
4986
|
100
|
66
|
|
|
47109
|
if ( (exists $opts{'delta'}) + |
177
|
|
|
|
|
|
|
(exists $opts{'business'}) + |
178
|
|
|
|
|
|
|
(exists $opts{'standard'}) + |
179
|
|
|
|
|
|
|
(exists $opts{'y'} || exists $opts{'M'} || exists $opts{'w'} || |
180
|
|
|
|
|
|
|
exists $opts{'d'} || exists $opts{'h'} || exists $opts{'m'} || |
181
|
|
|
|
|
|
|
exists $opts{'s'}) |
182
|
|
|
|
|
|
|
> 1 ) { |
183
|
2
|
|
|
|
|
5
|
$$self{'err'} = "[set] Fields set multiple times"; |
184
|
2
|
|
|
|
|
5
|
return 1; |
185
|
|
|
|
|
|
|
} |
186
|
|
|
|
|
|
|
|
187
|
4984
|
100
|
100
|
|
|
10700
|
if (exists $opts{'mode'} && $opts{'mode'} !~ /^(business|standard)$/) { |
188
|
1
|
|
|
|
|
3
|
$$self{'err'} = "[set] Unknown value for mode: $opts{mode}"; |
189
|
1
|
|
|
|
|
3
|
return 1; |
190
|
|
|
|
|
|
|
} |
191
|
4983
|
100
|
100
|
|
|
9510
|
if (exists $opts{'type'} && |
192
|
|
|
|
|
|
|
$opts{'type'} !~ /^(exact|semi|estimated|approx)$/) { |
193
|
1
|
|
|
|
|
3
|
$$self{'err'} = "[set] Unknown value for type: $opts{type}"; |
194
|
1
|
|
|
|
|
3
|
return 1; |
195
|
|
|
|
|
|
|
} |
196
|
|
|
|
|
|
|
|
197
|
4982
|
100
|
|
|
|
13562
|
if ( (exists $opts{'business'}) + |
|
|
100
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
198
|
|
|
|
|
|
|
(exists $opts{'standard'}) + |
199
|
|
|
|
|
|
|
(exists $opts{'mode'}) |
200
|
|
|
|
|
|
|
> 1 ) { |
201
|
1
|
|
|
|
|
3
|
$$self{'err'} = "[set] Mode set multiple times"; |
202
|
1
|
|
|
|
|
3
|
return 1; |
203
|
|
|
|
|
|
|
} elsif (exists $opts{'business'}) { |
204
|
166
|
|
|
|
|
254
|
$opts{'delta'} = $opts{'business'}; |
205
|
166
|
|
|
|
|
269
|
$opts{'mode'} = 'business'; |
206
|
|
|
|
|
|
|
} elsif (exists $opts{'standard'}) { |
207
|
8
|
|
|
|
|
18
|
$opts{'delta'} = $opts{'standard'}; |
208
|
8
|
|
|
|
|
39
|
$opts{'mode'} = 'standard'; |
209
|
|
|
|
|
|
|
} |
210
|
|
|
|
|
|
|
|
211
|
|
|
|
|
|
|
# If we are setting delta/business/standard, we need to initialize |
212
|
|
|
|
|
|
|
# all the parameters. |
213
|
|
|
|
|
|
|
|
214
|
4981
|
|
|
|
|
5856
|
my @delta; |
215
|
4981
|
100
|
|
|
|
7541
|
if (exists $opts{'delta'}) { |
216
|
4938
|
100
|
|
|
|
10027
|
if (ref($opts{'delta'}) ne 'ARRAY') { |
217
|
1
|
|
|
|
|
4
|
$$self{'err'} = "[set] Option delta requires an array value"; |
218
|
1
|
|
|
|
|
4
|
return 1; |
219
|
|
|
|
|
|
|
} |
220
|
|
|
|
|
|
|
|
221
|
|
|
|
|
|
|
# Init everything because we're setting an entire new delta |
222
|
4937
|
|
|
|
|
10205
|
$self->_init(); |
223
|
4937
|
|
|
|
|
7616
|
@delta = @{ $opts{'delta'} }; |
|
4937
|
|
|
|
|
10123
|
|
224
|
|
|
|
|
|
|
|
225
|
|
|
|
|
|
|
} else { |
226
|
43
|
|
|
|
|
53
|
@delta = @{ $$self{'data'}{'delta'} }; |
|
43
|
|
|
|
|
104
|
|
227
|
|
|
|
|
|
|
} |
228
|
|
|
|
|
|
|
|
229
|
|
|
|
|
|
|
# Figure out the parameters. Include the nonorm/mode/type |
230
|
|
|
|
|
|
|
# options. |
231
|
|
|
|
|
|
|
|
232
|
4980
|
|
|
|
|
5961
|
my $err; |
233
|
4980
|
|
|
|
|
6251
|
my $dmt = $$self{'tz'}; |
234
|
4980
|
|
|
|
|
5976
|
my $dmb = $$dmt{'base'}; |
235
|
4980
|
100
|
|
|
|
8639
|
my $gotmode = (exists $opts{'mode'} ? 1 : $$self{'data'}{'gotmode'}); |
236
|
|
|
|
|
|
|
my $mode = (exists $opts{'mode'} ? $opts{'mode'} : |
237
|
4980
|
100
|
|
|
|
9016
|
$$self{'data'}{'mode'}); |
238
|
4980
|
100
|
|
|
|
7530
|
my $nonorm = (exists $opts{'nonorm'} ? $opts{'nonorm'} : 0); |
239
|
|
|
|
|
|
|
|
240
|
4980
|
|
|
|
|
6391
|
my ($type,$type_from); |
241
|
4980
|
100
|
|
|
|
7146
|
if (exists $opts{'type'}) { |
242
|
94
|
|
|
|
|
156
|
$type = $opts{'type'}; |
243
|
94
|
|
|
|
|
140
|
$type_from = 'opt'; |
244
|
|
|
|
|
|
|
} else { |
245
|
4886
|
|
|
|
|
6666
|
$type = $$self{'data'}{'type'}; |
246
|
4886
|
|
|
|
|
6333
|
$type_from = $$self{'data'}{'type_from'}; |
247
|
|
|
|
|
|
|
} |
248
|
|
|
|
|
|
|
|
249
|
|
|
|
|
|
|
# If we're setting individual fields, do that now |
250
|
|
|
|
|
|
|
|
251
|
|
|
|
|
|
|
{ |
252
|
4980
|
|
|
|
|
5816
|
my $field_set = 0; |
|
4980
|
|
|
|
|
5561
|
|
253
|
|
|
|
|
|
|
|
254
|
|
|
|
|
|
|
# Check all individual fields |
255
|
4980
|
|
|
|
|
7842
|
foreach my $opt (qw(y M w d h m s)) { |
256
|
34848
|
100
|
|
|
|
50358
|
if (exists $opts{$opt}) { |
257
|
8
|
100
|
|
|
|
19
|
if (ref($opts{$opt})) { |
258
|
1
|
|
|
|
|
4
|
$$self{'err'} = "[set] Option $opt requires a scalar value"; |
259
|
1
|
|
|
|
|
4
|
return 1; |
260
|
|
|
|
|
|
|
} |
261
|
7
|
|
|
|
|
12
|
my $val = $opts{$opt}; |
262
|
7
|
100
|
|
|
|
22
|
if (! $dmb->_is_num($val)) { |
263
|
1
|
|
|
|
|
5
|
$$self{'err'} = "[set] Option $opt requires a numerical value"; |
264
|
1
|
|
|
|
|
6
|
return 1; |
265
|
|
|
|
|
|
|
} |
266
|
6
|
|
|
|
|
13
|
$delta[ $f{$opt} ] = $val; |
267
|
6
|
|
|
|
|
10
|
$field_set = 1; |
268
|
|
|
|
|
|
|
} |
269
|
|
|
|
|
|
|
} |
270
|
|
|
|
|
|
|
|
271
|
|
|
|
|
|
|
# If none were set, than we're done with setting. |
272
|
4978
|
100
|
|
|
|
9486
|
last if (! $field_set); |
273
|
|
|
|
|
|
|
|
274
|
6
|
50
|
|
|
|
12
|
if ($$self{'err'}) { |
275
|
0
|
|
|
|
|
0
|
return 1; |
276
|
|
|
|
|
|
|
} |
277
|
|
|
|
|
|
|
} |
278
|
|
|
|
|
|
|
|
279
|
|
|
|
|
|
|
# Check that the type is consistent with @delta. |
280
|
|
|
|
|
|
|
|
281
|
4978
|
|
|
|
|
14866
|
($err,$type,$type_from) = |
282
|
|
|
|
|
|
|
$dmb->_check_delta_type($mode,$type,$type_from,@delta); |
283
|
|
|
|
|
|
|
|
284
|
4978
|
100
|
|
|
|
9386
|
if ($err) { |
285
|
11
|
|
|
|
|
24
|
$$self{'err'} = "[set] $err"; |
286
|
11
|
|
|
|
|
35
|
return 1; |
287
|
|
|
|
|
|
|
} |
288
|
|
|
|
|
|
|
|
289
|
4967
|
|
|
|
|
16276
|
my %o = ( 'source' => 'delta', |
290
|
|
|
|
|
|
|
'nonorm' => $nonorm, |
291
|
|
|
|
|
|
|
'type' => $type, |
292
|
|
|
|
|
|
|
'sign' => -1, |
293
|
|
|
|
|
|
|
'mode' => $mode, |
294
|
|
|
|
|
|
|
); |
295
|
|
|
|
|
|
|
|
296
|
4967
|
|
|
|
|
17432
|
($err,@delta) = $dmb->_delta_fields( \%o, [@delta]); |
297
|
|
|
|
|
|
|
|
298
|
4967
|
100
|
|
|
|
11486
|
if ($err) { |
299
|
2
|
|
|
|
|
6
|
$$self{'err'} = "[set] $err"; |
300
|
2
|
|
|
|
|
8
|
return 1; |
301
|
|
|
|
|
|
|
} |
302
|
|
|
|
|
|
|
|
303
|
4965
|
|
|
|
|
13530
|
$$self{'data'}{'delta'} = [ @delta ]; |
304
|
4965
|
|
|
|
|
7420
|
$$self{'data'}{'mode'} = $mode; |
305
|
4965
|
|
|
|
|
6313
|
$$self{'data'}{'gotmode'} = $gotmode; |
306
|
4965
|
|
|
|
|
6510
|
$$self{'data'}{'type'} = $type; |
307
|
4965
|
|
|
|
|
6498
|
$$self{'data'}{'type_from'} = $type_from; |
308
|
4965
|
|
|
|
|
6940
|
$$self{'data'}{'normalized'} = 1-$nonorm; |
309
|
4965
|
|
|
|
|
6849
|
$$self{'data'}{'length'} = 'unknown'; |
310
|
4965
|
|
|
|
|
6633
|
$$self{'data'}{'in'} = ''; |
311
|
|
|
|
|
|
|
|
312
|
4965
|
|
|
|
|
17260
|
return 0; |
313
|
|
|
|
|
|
|
} |
314
|
|
|
|
|
|
|
} |
315
|
|
|
|
|
|
|
|
316
|
|
|
|
|
|
|
sub _rx { |
317
|
2101
|
|
|
2101
|
|
2864
|
my($self,$rx) = @_; |
318
|
2101
|
|
|
|
|
2536
|
my $dmt = $$self{'tz'}; |
319
|
2101
|
|
|
|
|
2283
|
my $dmb = $$dmt{'base'}; |
320
|
|
|
|
|
|
|
|
321
|
|
|
|
|
|
|
return $$dmb{'data'}{'rx'}{'delta'}{$rx} |
322
|
2101
|
100
|
|
|
|
4826
|
if (exists $$dmb{'data'}{'rx'}{'delta'}{$rx}); |
323
|
|
|
|
|
|
|
|
324
|
84
|
100
|
|
|
|
435
|
if ($rx eq 'expanded') { |
|
|
100
|
|
|
|
|
|
|
|
50
|
|
|
|
|
|
325
|
26
|
|
|
|
|
57
|
my $sign = '[-+]?\s*'; |
326
|
26
|
|
|
|
|
52
|
my $sep = '(?:,\s*|\s+|$)'; |
327
|
|
|
|
|
|
|
|
328
|
26
|
|
|
|
|
83
|
my $nth = $$dmb{'data'}{'rx'}{'nth'}[0]; |
329
|
26
|
|
|
|
|
75
|
my $yf = $$dmb{data}{rx}{fields}[1]; |
330
|
26
|
|
|
|
|
63
|
my $mf = $$dmb{data}{rx}{fields}[2]; |
331
|
26
|
|
|
|
|
69
|
my $wf = $$dmb{data}{rx}{fields}[3]; |
332
|
26
|
|
|
|
|
56
|
my $df = $$dmb{data}{rx}{fields}[4]; |
333
|
26
|
|
|
|
|
62
|
my $hf = $$dmb{data}{rx}{fields}[5]; |
334
|
26
|
|
|
|
|
57
|
my $mnf = $$dmb{data}{rx}{fields}[6]; |
335
|
26
|
|
|
|
|
62
|
my $sf = $$dmb{data}{rx}{fields}[7]; |
336
|
26
|
|
|
|
|
48
|
my $num = '(?:\d+(?:\.\d*)?|\.\d+)'; |
337
|
|
|
|
|
|
|
|
338
|
26
|
|
|
|
|
196
|
my $y = "(?:(?:(?<y>$sign$num)|(?<y>$nth))\\s*(?:$yf)$sep)"; |
339
|
26
|
|
|
|
|
170
|
my $m = "(?:(?:(?<m>$sign$num)|(?<m>$nth))\\s*(?:$mf)$sep)"; |
340
|
26
|
|
|
|
|
152
|
my $w = "(?:(?:(?<w>$sign$num)|(?<w>$nth))\\s*(?:$wf)$sep)"; |
341
|
26
|
|
|
|
|
151
|
my $d = "(?:(?:(?<d>$sign$num)|(?<d>$nth))\\s*(?:$df)$sep)"; |
342
|
26
|
|
|
|
|
155
|
my $h = "(?:(?:(?<h>$sign$num)|(?<h>$nth))\\s*(?:$hf)$sep)"; |
343
|
26
|
|
|
|
|
198
|
my $mn = "(?:(?:(?<mn>$sign$num)|(?<mn>$nth))\\s*(?:$mnf)$sep)"; |
344
|
26
|
|
|
|
|
193
|
my $s = "(?:(?:(?<s>$sign$num)|(?<s>$nth))\\s*(?:$sf)?)"; |
345
|
|
|
|
|
|
|
|
346
|
26
|
|
|
|
|
117841
|
my $exprx = qr/^\s*$y?$m?$w?$d?$h?$mn?$s?\s*$/i; |
347
|
26
|
|
|
|
|
1632
|
$$dmb{'data'}{'rx'}{'delta'}{$rx} = $exprx; |
348
|
|
|
|
|
|
|
|
349
|
|
|
|
|
|
|
} elsif ($rx eq 'mode') { |
350
|
|
|
|
|
|
|
|
351
|
32
|
|
|
|
|
692
|
my $mode = qr/\b($$dmb{'data'}{'rx'}{'mode'}[0])\b/i; |
352
|
32
|
|
|
|
|
130
|
$$dmb{'data'}{'rx'}{'delta'}{$rx} = $mode; |
353
|
|
|
|
|
|
|
|
354
|
|
|
|
|
|
|
} elsif ($rx eq 'when') { |
355
|
|
|
|
|
|
|
|
356
|
26
|
|
|
|
|
1224
|
my $when = qr/\b($$dmb{'data'}{'rx'}{'when'}[0])\b/i; |
357
|
26
|
|
|
|
|
114
|
$$dmb{'data'}{'rx'}{'delta'}{$rx} = $when; |
358
|
|
|
|
|
|
|
|
359
|
|
|
|
|
|
|
} |
360
|
|
|
|
|
|
|
|
361
|
84
|
|
|
|
|
241
|
return $$dmb{'data'}{'rx'}{'delta'}{$rx}; |
362
|
|
|
|
|
|
|
} |
363
|
|
|
|
|
|
|
|
364
|
|
|
|
|
|
|
sub parse { |
365
|
773
|
|
|
773
|
1
|
175477
|
my($self,$instring,@args) = @_; |
366
|
773
|
|
|
|
|
1697
|
$self->_init(); |
367
|
|
|
|
|
|
|
|
368
|
773
|
|
|
|
|
1152
|
my %opts; |
369
|
773
|
50
|
|
|
|
1630
|
if (ref($args[0]) eq 'HASH') { |
370
|
0
|
|
|
|
|
0
|
%opts = %{ $args[0] }; |
|
0
|
|
|
|
|
0
|
|
371
|
|
|
|
|
|
|
|
372
|
|
|
|
|
|
|
} else { |
373
|
|
|
|
|
|
|
# *** DEPRECATED 7.0 *** |
374
|
|
|
|
|
|
|
|
375
|
773
|
|
|
|
|
993
|
my($business,$no_normalize); |
376
|
|
|
|
|
|
|
|
377
|
773
|
50
|
|
|
|
2374
|
if (@args == 2) { |
|
|
100
|
|
|
|
|
|
|
|
50
|
|
|
|
|
|
378
|
0
|
|
|
|
|
0
|
($business,$no_normalize) = (lc($args[0]),lc($args[1])); |
379
|
0
|
0
|
0
|
|
|
0
|
if ($business eq 'standard' || ! $business) { |
380
|
0
|
|
|
|
|
0
|
$opts{'mode'} = 'standard'; |
381
|
|
|
|
|
|
|
} else { |
382
|
0
|
|
|
|
|
0
|
$opts{'mode'} = 'business'; |
383
|
|
|
|
|
|
|
} |
384
|
|
|
|
|
|
|
|
385
|
0
|
0
|
|
|
|
0
|
$opts{'nonorm'} = ($no_normalize ? 1 : 0); |
386
|
|
|
|
|
|
|
|
387
|
|
|
|
|
|
|
} elsif (@args == 1) { |
388
|
1
|
|
|
|
|
3
|
my $arg = lc($args[0]); |
389
|
1
|
50
|
|
|
|
6
|
if ($arg eq 'standard') { |
|
|
50
|
|
|
|
|
|
|
|
0
|
|
|
|
|
|
|
|
0
|
|
|
|
|
|
390
|
0
|
|
|
|
|
0
|
$opts{'mode'} = 'standard'; |
391
|
|
|
|
|
|
|
} elsif ($arg eq 'business') { |
392
|
1
|
|
|
|
|
4
|
$opts{'mode'} = 'business'; |
393
|
|
|
|
|
|
|
} elsif ($arg eq 'nonormalize') { |
394
|
0
|
|
|
|
|
0
|
$opts{'nonorm'} = 1; |
395
|
|
|
|
|
|
|
} elsif ($arg) { |
396
|
0
|
|
|
|
|
0
|
$opts{'mode'} = 'business'; |
397
|
|
|
|
|
|
|
} else { |
398
|
0
|
|
|
|
|
0
|
$opts{'mode'} = 'standard'; |
399
|
|
|
|
|
|
|
} |
400
|
|
|
|
|
|
|
|
401
|
|
|
|
|
|
|
} elsif (@args) { |
402
|
0
|
|
|
|
|
0
|
$$self{'err'} = "[parse] Unknown arguments"; |
403
|
0
|
|
|
|
|
0
|
return 1; |
404
|
|
|
|
|
|
|
} |
405
|
|
|
|
|
|
|
} |
406
|
|
|
|
|
|
|
|
407
|
773
|
|
|
|
|
1258
|
my $dmt = $$self{'tz'}; |
408
|
773
|
|
|
|
|
961
|
my $dmb = $$dmt{'base'}; |
409
|
773
|
|
|
|
|
1470
|
$self->_init(); |
410
|
|
|
|
|
|
|
|
411
|
773
|
50
|
|
|
|
1529
|
if (! $instring) { |
412
|
0
|
|
|
|
|
0
|
$$self{'err'} = '[parse] Empty delta string'; |
413
|
0
|
|
|
|
|
0
|
return 1; |
414
|
|
|
|
|
|
|
} |
415
|
|
|
|
|
|
|
|
416
|
|
|
|
|
|
|
# |
417
|
|
|
|
|
|
|
# Parse the string |
418
|
|
|
|
|
|
|
# $err : any error |
419
|
|
|
|
|
|
|
# @delta : the delta parsed |
420
|
|
|
|
|
|
|
# $mode : the mode string (if any) in the string |
421
|
|
|
|
|
|
|
# |
422
|
|
|
|
|
|
|
|
423
|
773
|
|
|
|
|
1000
|
my ($err,@delta,$mode); |
424
|
773
|
|
|
|
|
1000
|
$mode = ''; |
425
|
773
|
|
|
|
|
970
|
$$self{'err'} = ''; |
426
|
773
|
|
|
|
|
2666
|
$instring =~ s/^\s*//; |
427
|
773
|
|
|
|
|
3505
|
$instring =~ s/\s*$//; |
428
|
|
|
|
|
|
|
|
429
|
|
|
|
|
|
|
PARSE: { |
430
|
|
|
|
|
|
|
|
431
|
|
|
|
|
|
|
# First, we'll try the standard format (without a mode string) |
432
|
|
|
|
|
|
|
|
433
|
773
|
|
|
|
|
1168
|
($err,@delta) = $dmb->_split_delta($instring); |
|
773
|
|
|
|
|
2133
|
|
434
|
773
|
100
|
|
|
|
1683
|
last PARSE if (! $err); |
435
|
|
|
|
|
|
|
|
436
|
|
|
|
|
|
|
# Next, we'll need to get a list of all the encodings and look |
437
|
|
|
|
|
|
|
# for (and remove) the mode string from each. We'll also recheck |
438
|
|
|
|
|
|
|
# the standard format for each. |
439
|
|
|
|
|
|
|
|
440
|
513
|
|
|
|
|
1276
|
my @strings = $dmb->_encoding($instring); |
441
|
513
|
|
|
|
|
1149
|
my $moderx = $self->_rx('mode'); |
442
|
|
|
|
|
|
|
|
443
|
513
|
|
|
|
|
867
|
foreach my $string (@strings) { |
444
|
1010
|
100
|
|
|
|
8010
|
if ($string =~ s/\s*$moderx\s*//i) { |
445
|
174
|
|
|
|
|
402
|
my $m = $1; |
446
|
174
|
100
|
|
|
|
562
|
if ($$dmb{'data'}{'wordmatch'}{'mode'}{lc($m)} == 1) { |
447
|
1
|
|
|
|
|
2
|
$m = 'standard'; |
448
|
|
|
|
|
|
|
} else { |
449
|
173
|
|
|
|
|
233
|
$m = 'business'; |
450
|
|
|
|
|
|
|
} |
451
|
174
|
|
|
|
|
208
|
$mode = $m; |
452
|
|
|
|
|
|
|
|
453
|
174
|
|
|
|
|
350
|
($err,@delta) = $dmb->_split_delta($string); |
454
|
174
|
100
|
|
|
|
496
|
last PARSE if (! $err); |
455
|
|
|
|
|
|
|
} |
456
|
|
|
|
|
|
|
} |
457
|
|
|
|
|
|
|
|
458
|
|
|
|
|
|
|
# Now we'll check each string for an expanded form delta. |
459
|
|
|
|
|
|
|
|
460
|
424
|
|
|
|
|
669
|
foreach my $string (@strings) { |
461
|
794
|
|
|
|
|
1036
|
my $past = 0; |
462
|
|
|
|
|
|
|
|
463
|
794
|
|
|
|
|
1256
|
my $whenrx = $self->_rx('when'); |
464
|
794
|
100
|
66
|
|
|
5089
|
if ($string && |
465
|
|
|
|
|
|
|
$string =~ s/$whenrx//i) { |
466
|
50
|
|
|
|
|
119
|
my $when = $1; |
467
|
50
|
100
|
|
|
|
182
|
if ($$dmb{'data'}{'wordmatch'}{'when'}{lc($when)} == 1) { |
468
|
16
|
|
|
|
|
41
|
$past = 1; |
469
|
|
|
|
|
|
|
} |
470
|
|
|
|
|
|
|
} |
471
|
|
|
|
|
|
|
|
472
|
794
|
|
|
|
|
1379
|
my $rx = $self->_rx('expanded'); |
473
|
794
|
100
|
66
|
|
|
12889
|
if ($string && |
474
|
|
|
|
|
|
|
$string =~ $rx) { |
475
|
114
|
|
|
|
|
1442
|
@delta = @+{qw(y m w d h mn s)}; |
476
|
114
|
|
|
|
|
381
|
foreach my $f (@delta) { |
477
|
798
|
100
|
|
|
|
1316
|
if (! defined $f) { |
|
|
100
|
|
|
|
|
|
478
|
660
|
|
|
|
|
733
|
$f = 0; |
479
|
|
|
|
|
|
|
} elsif (exists $$dmb{'data'}{'wordmatch'}{'nth'}{lc($f)}) { |
480
|
4
|
|
|
|
|
12
|
$f = $$dmb{'data'}{'wordmatch'}{'nth'}{lc($f)}; |
481
|
|
|
|
|
|
|
} else { |
482
|
134
|
|
|
|
|
379
|
$f =~ s/\s//g; |
483
|
|
|
|
|
|
|
} |
484
|
|
|
|
|
|
|
} |
485
|
|
|
|
|
|
|
|
486
|
|
|
|
|
|
|
# if $past, reverse the signs |
487
|
114
|
100
|
|
|
|
217
|
if ($past) { |
488
|
12
|
|
|
|
|
31
|
foreach my $v (@delta) { |
489
|
84
|
|
|
|
|
99
|
$v *= -1; |
490
|
|
|
|
|
|
|
} |
491
|
|
|
|
|
|
|
} |
492
|
|
|
|
|
|
|
|
493
|
114
|
|
|
|
|
273
|
last PARSE; |
494
|
|
|
|
|
|
|
} |
495
|
|
|
|
|
|
|
} |
496
|
|
|
|
|
|
|
} |
497
|
|
|
|
|
|
|
|
498
|
773
|
100
|
|
|
|
1633
|
if (! @delta) { |
499
|
310
|
|
|
|
|
516
|
$$self{'err'} = "[parse] Invalid delta string"; |
500
|
310
|
|
|
|
|
875
|
return 1; |
501
|
|
|
|
|
|
|
} |
502
|
|
|
|
|
|
|
|
503
|
|
|
|
|
|
|
# If the string contains a mode string and the mode was passed in |
504
|
|
|
|
|
|
|
# as an option, they must be identical. |
505
|
|
|
|
|
|
|
|
506
|
463
|
50
|
66
|
|
|
1089
|
if ($mode && exists($opts{'mode'}) && $mode ne $opts{'mode'}) { |
|
|
|
33
|
|
|
|
|
507
|
0
|
|
|
|
|
0
|
$$self{'err'} = |
508
|
|
|
|
|
|
|
"[parse] Mode option conflicts with mode specified in string"; |
509
|
0
|
|
|
|
|
0
|
return 1; |
510
|
|
|
|
|
|
|
} |
511
|
463
|
100
|
|
|
|
841
|
$mode = $opts{'mode'} if (exists $opts{'mode'}); |
512
|
463
|
100
|
|
|
|
847
|
$mode = 'standard' if (! $mode); |
513
|
|
|
|
|
|
|
|
514
|
|
|
|
|
|
|
# Figure out the type. |
515
|
|
|
|
|
|
|
|
516
|
|
|
|
|
|
|
my %o = ( 'source' => 'string', |
517
|
463
|
50
|
|
|
|
1714
|
'nonorm' => (exists $opts{'nonorm'} ? $opts{'nonorm'} : 0), |
518
|
|
|
|
|
|
|
'sign' => -1, |
519
|
|
|
|
|
|
|
'mode' => $mode, |
520
|
|
|
|
|
|
|
); |
521
|
|
|
|
|
|
|
|
522
|
463
|
|
|
|
|
2003
|
($err,@delta) = $dmb->_delta_fields( \%o, [@delta]); |
523
|
463
|
|
|
|
|
1027
|
my $type = $o{'type'}; |
524
|
463
|
|
|
|
|
634
|
my $type_from = $o{'type_from'}; |
525
|
|
|
|
|
|
|
|
526
|
463
|
50
|
|
|
|
794
|
if ($err) { |
527
|
0
|
|
|
|
|
0
|
$$self{'err'} = "[parse] $err"; |
528
|
0
|
|
|
|
|
0
|
return 1; |
529
|
|
|
|
|
|
|
} |
530
|
|
|
|
|
|
|
|
531
|
463
|
|
|
|
|
946
|
$$self{'data'}{'in'} = $instring; |
532
|
463
|
|
|
|
|
1151
|
$$self{'data'}{'delta'} = [@delta]; |
533
|
463
|
|
|
|
|
745
|
$$self{'data'}{'mode'} = $mode; |
534
|
463
|
50
|
33
|
|
|
1218
|
$$self{'data'}{'gotmode'} = ($mode || exists $opts{'mode'} ? 1 : 0); |
535
|
463
|
|
|
|
|
637
|
$$self{'data'}{'type'} = $type; |
536
|
463
|
|
|
|
|
581
|
$$self{'data'}{'type_from'} = $type_from; |
537
|
463
|
|
|
|
|
662
|
$$self{'data'}{'length'} = 'unknown'; |
538
|
463
|
50
|
|
|
|
846
|
$$self{'data'}{'normalized'} = ($opts{'nonorm'} ? 0 : 1); |
539
|
|
|
|
|
|
|
|
540
|
463
|
|
|
|
|
1523
|
return 0; |
541
|
|
|
|
|
|
|
} |
542
|
|
|
|
|
|
|
|
543
|
|
|
|
|
|
|
sub printf { |
544
|
2350
|
|
|
2350
|
1
|
4853
|
my($self,@in) = @_; |
545
|
2350
|
50
|
|
|
|
4954
|
if ($$self{'err'}) { |
546
|
0
|
|
|
|
|
0
|
carp "WARNING: [printf] Object must contain a valid delta"; |
547
|
0
|
|
|
|
|
0
|
return undef; |
548
|
|
|
|
|
|
|
} |
549
|
|
|
|
|
|
|
|
550
|
2350
|
|
|
|
|
2866
|
my($y,$M,$w,$d,$h,$m,$s) = @{ $$self{'data'}{'delta'} }; |
|
2350
|
|
|
|
|
6286
|
|
551
|
|
|
|
|
|
|
|
552
|
2350
|
|
|
|
|
3115
|
my @out; |
553
|
2350
|
|
|
|
|
3657
|
foreach my $in (@in) { |
554
|
2352
|
|
|
|
|
3209
|
my $out = ''; |
555
|
2352
|
|
|
|
|
4042
|
while ($in) { |
556
|
2812
|
100
|
|
|
|
22695
|
if ($in =~ s/^([^%]+)//) { |
|
|
100
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
|
50
|
|
|
|
|
|
557
|
268
|
|
|
|
|
596
|
$out .= $1; |
558
|
|
|
|
|
|
|
|
559
|
|
|
|
|
|
|
} elsif ($in =~ s/^%%//) { |
560
|
1
|
|
|
|
|
3
|
$out .= "%"; |
561
|
|
|
|
|
|
|
|
562
|
|
|
|
|
|
|
} elsif ($in =~ s/^% |
563
|
|
|
|
|
|
|
(\+)? # sign |
564
|
|
|
|
|
|
|
([<>0])? # pad |
565
|
|
|
|
|
|
|
(\d+)? # width |
566
|
|
|
|
|
|
|
([yMwdhms]) # field |
567
|
|
|
|
|
|
|
v # type |
568
|
|
|
|
|
|
|
//ox) { |
569
|
18
|
|
|
|
|
48
|
my($sign,$pad,$width,$field) = ($1,$2,$3,$4); |
570
|
18
|
|
|
|
|
39
|
$out .= $self->_printf_field($sign,$pad,$width,0,$field); |
571
|
|
|
|
|
|
|
|
572
|
|
|
|
|
|
|
} elsif ($in =~ s/^(% |
573
|
|
|
|
|
|
|
(\+)? # sign |
574
|
|
|
|
|
|
|
([<>0])? # pad |
575
|
|
|
|
|
|
|
(\d+)? # width |
576
|
|
|
|
|
|
|
(?:\.(\d+))? # precision |
577
|
|
|
|
|
|
|
([yMwdhms]) # field |
578
|
|
|
|
|
|
|
([yMwdhms]) # field0 |
579
|
|
|
|
|
|
|
([yMwdhms]) # field1 |
580
|
|
|
|
|
|
|
)//ox) { |
581
|
2503
|
|
|
|
|
12035
|
my($match,$sign,$pad,$width,$precision,$field,$field0,$field1) = |
582
|
|
|
|
|
|
|
($1,$2,$3,$4,$5,$6,$7,$8); |
583
|
|
|
|
|
|
|
|
584
|
|
|
|
|
|
|
# Get the list of fields we're expressing |
585
|
|
|
|
|
|
|
|
586
|
2503
|
|
|
|
|
6247
|
my @field = qw(y M w d h m s); |
587
|
2503
|
|
66
|
|
|
9455
|
while (@field && $field[0] ne $field0) { |
588
|
338
|
|
|
|
|
737
|
shift(@field); |
589
|
|
|
|
|
|
|
} |
590
|
2503
|
|
66
|
|
|
8147
|
while (@field && $field[$#field] ne $field1) { |
591
|
342
|
|
|
|
|
700
|
pop(@field); |
592
|
|
|
|
|
|
|
} |
593
|
|
|
|
|
|
|
|
594
|
2503
|
50
|
|
|
|
4461
|
if (! @field) { |
595
|
0
|
|
|
|
|
0
|
$out .= $match; |
596
|
|
|
|
|
|
|
} else { |
597
|
2503
|
|
|
|
|
5986
|
$out .= |
598
|
|
|
|
|
|
|
$self->_printf_field($sign,$pad,$width,$precision,$field,@field); |
599
|
|
|
|
|
|
|
} |
600
|
|
|
|
|
|
|
|
601
|
|
|
|
|
|
|
} elsif ($in =~ s/^% |
602
|
|
|
|
|
|
|
(\+)? # sign |
603
|
|
|
|
|
|
|
([<>])? # pad |
604
|
|
|
|
|
|
|
(\d+)? # width |
605
|
|
|
|
|
|
|
Dt |
606
|
|
|
|
|
|
|
//ox) { |
607
|
6
|
|
|
|
|
16
|
my($sign,$pad,$width) = ($1,$2,$3); |
608
|
6
|
|
|
|
|
15
|
$out .= $self->_printf_delta($sign,$pad,$width,'y','s'); |
609
|
|
|
|
|
|
|
|
610
|
|
|
|
|
|
|
} elsif ($in =~ s/^(% |
611
|
|
|
|
|
|
|
(\+)? # sign |
612
|
|
|
|
|
|
|
([<>])? # pad |
613
|
|
|
|
|
|
|
(\d+)? # width |
614
|
|
|
|
|
|
|
D |
615
|
|
|
|
|
|
|
([yMwdhms]) # field0 |
616
|
|
|
|
|
|
|
([yMwdhms]) # field1 |
617
|
|
|
|
|
|
|
)//ox) { |
618
|
16
|
|
|
|
|
52
|
my($match,$sign,$pad,$width,$field0,$field1) = ($1,$2,$3,$4,$5,$6); |
619
|
|
|
|
|
|
|
|
620
|
|
|
|
|
|
|
# Get the list of fields we're expressing |
621
|
|
|
|
|
|
|
|
622
|
16
|
|
|
|
|
32
|
my @field = qw(y M w d h m s); |
623
|
16
|
|
66
|
|
|
61
|
while (@field && $field[0] ne $field0) { |
624
|
7
|
|
|
|
|
15
|
shift(@field); |
625
|
|
|
|
|
|
|
} |
626
|
16
|
|
66
|
|
|
42
|
while (@field && $field[$#field] ne $field1) { |
627
|
59
|
|
|
|
|
127
|
pop(@field); |
628
|
|
|
|
|
|
|
} |
629
|
|
|
|
|
|
|
|
630
|
16
|
50
|
|
|
|
24
|
if (! @field) { |
631
|
0
|
|
|
|
|
0
|
$out .= $match; |
632
|
|
|
|
|
|
|
} else { |
633
|
16
|
|
|
|
|
33
|
$out .= $self->_printf_delta($sign,$pad,$width,$field[0], |
634
|
|
|
|
|
|
|
$field[$#field]); |
635
|
|
|
|
|
|
|
} |
636
|
|
|
|
|
|
|
|
637
|
|
|
|
|
|
|
} else { |
638
|
0
|
|
|
|
|
0
|
$in =~ s/^(%[^%]*)//; |
639
|
0
|
|
|
|
|
0
|
$out .= $1; |
640
|
|
|
|
|
|
|
} |
641
|
|
|
|
|
|
|
} |
642
|
2352
|
|
|
|
|
4607
|
push(@out,$out); |
643
|
|
|
|
|
|
|
} |
644
|
|
|
|
|
|
|
|
645
|
2350
|
100
|
|
|
|
5674
|
if (wantarray) { |
|
|
50
|
|
|
|
|
|
646
|
58
|
|
|
|
|
198
|
return @out; |
647
|
|
|
|
|
|
|
} elsif (@out == 1) { |
648
|
2292
|
|
|
|
|
6781
|
return $out[0]; |
649
|
|
|
|
|
|
|
} |
650
|
|
|
|
|
|
|
|
651
|
0
|
|
|
|
|
0
|
return '' |
652
|
|
|
|
|
|
|
} |
653
|
|
|
|
|
|
|
|
654
|
|
|
|
|
|
|
sub _printf_delta { |
655
|
22
|
|
|
22
|
|
42
|
my($self,$sign,$pad,$width,$field0,$field1) = @_; |
656
|
22
|
|
|
|
|
27
|
my $dmt = $$self{'tz'}; |
657
|
22
|
|
|
|
|
26
|
my $dmb = $$dmt{'base'}; |
658
|
22
|
|
|
|
|
25
|
my @delta = @{ $$self{'data'}{'delta'} }; |
|
22
|
|
|
|
|
41
|
|
659
|
22
|
|
|
|
|
27
|
my $delta; |
660
|
22
|
|
|
|
|
75
|
my %tmp = qw(y 0 M 1 w 2 d 3 h 4 m 5 s 6); |
661
|
|
|
|
|
|
|
|
662
|
|
|
|
|
|
|
# Add a sign to each field |
663
|
|
|
|
|
|
|
|
664
|
22
|
|
|
|
|
30
|
my $s = "+"; |
665
|
22
|
|
|
|
|
23
|
foreach my $f (@delta) { |
666
|
154
|
100
|
|
|
|
222
|
if ($f < 0) { |
|
|
100
|
|
|
|
|
|
667
|
13
|
|
|
|
|
15
|
$s = "-"; |
668
|
|
|
|
|
|
|
} elsif ($f > 0) { |
669
|
116
|
|
|
|
|
109
|
$s = "+"; |
670
|
116
|
|
|
|
|
110
|
$f *= 1; |
671
|
116
|
|
|
|
|
159
|
$f = "+$f"; |
672
|
|
|
|
|
|
|
} else { |
673
|
25
|
|
|
|
|
40
|
$f = "$s$f"; |
674
|
|
|
|
|
|
|
} |
675
|
|
|
|
|
|
|
} |
676
|
|
|
|
|
|
|
|
677
|
|
|
|
|
|
|
# Split the delta into field sets containing only those fields to |
678
|
|
|
|
|
|
|
# print. |
679
|
|
|
|
|
|
|
# |
680
|
|
|
|
|
|
|
# @set = ( [SETa] [SETb] ....) |
681
|
|
|
|
|
|
|
# where [SETx] is a listref of fields from one set of fields |
682
|
|
|
|
|
|
|
|
683
|
22
|
|
|
|
|
24
|
my @set; |
684
|
22
|
|
|
|
|
29
|
my $mode = $$self{'data'}{'mode'}; |
685
|
|
|
|
|
|
|
|
686
|
22
|
|
|
|
|
25
|
my $f0 = $tmp{$field0}; |
687
|
22
|
|
|
|
|
25
|
my $f1 = $tmp{$field1}; |
688
|
|
|
|
|
|
|
|
689
|
22
|
100
|
|
|
|
39
|
if ($field0 eq $field1) { |
|
|
100
|
|
|
|
|
|
690
|
3
|
|
|
|
|
7
|
@set = ( [ $delta[$f0] ] ); |
691
|
|
|
|
|
|
|
|
692
|
|
|
|
|
|
|
} elsif ($mode eq 'business') { |
693
|
|
|
|
|
|
|
|
694
|
4
|
100
|
|
|
|
8
|
if ($f0 <= 1) { |
695
|
|
|
|
|
|
|
# if (field0 = y or M) |
696
|
|
|
|
|
|
|
# add [y,M] |
697
|
|
|
|
|
|
|
# if field1 = M |
698
|
|
|
|
|
|
|
# done |
699
|
|
|
|
|
|
|
# else |
700
|
|
|
|
|
|
|
# field0 = w |
701
|
3
|
|
|
|
|
10
|
push(@set, [ @delta[$f0..1] ]); |
702
|
3
|
100
|
|
|
|
8
|
$f0 = ($f1 == 1 ? 7 : 2); |
703
|
|
|
|
|
|
|
} |
704
|
|
|
|
|
|
|
|
705
|
4
|
100
|
|
|
|
6
|
if ($f0 == 2) { |
706
|
|
|
|
|
|
|
# if (field0 = w) |
707
|
|
|
|
|
|
|
# add [w] |
708
|
|
|
|
|
|
|
# if field1 = w |
709
|
|
|
|
|
|
|
# done |
710
|
|
|
|
|
|
|
# else |
711
|
|
|
|
|
|
|
# field0 = d |
712
|
2
|
|
|
|
|
3
|
push(@set, [ $delta[2] ]); |
713
|
2
|
50
|
|
|
|
5
|
$f0 = ($f1 == 2 ? 7 : 3); |
714
|
|
|
|
|
|
|
} |
715
|
|
|
|
|
|
|
|
716
|
4
|
100
|
|
|
|
8
|
if ($f0 <= 6) { |
717
|
3
|
|
|
|
|
10
|
push(@set, [ @delta[$f0..$f1] ]); |
718
|
|
|
|
|
|
|
} |
719
|
|
|
|
|
|
|
|
720
|
|
|
|
|
|
|
} else { |
721
|
|
|
|
|
|
|
|
722
|
15
|
100
|
|
|
|
25
|
if ($f0 <= 1) { |
723
|
|
|
|
|
|
|
# if (field0 = y or M) |
724
|
|
|
|
|
|
|
# add [y,M] |
725
|
|
|
|
|
|
|
# if field1 = M |
726
|
|
|
|
|
|
|
# done |
727
|
|
|
|
|
|
|
# else |
728
|
|
|
|
|
|
|
# field0 = w |
729
|
14
|
|
|
|
|
35
|
push(@set, [ @delta[$f0..1] ]); |
730
|
14
|
100
|
|
|
|
23
|
$f0 = ($f1 == 1 ? 7 : 2); |
731
|
|
|
|
|
|
|
} |
732
|
|
|
|
|
|
|
|
733
|
15
|
100
|
|
|
|
26
|
if ($f0 <= 3) { |
734
|
|
|
|
|
|
|
# if (field0 = w or d) |
735
|
|
|
|
|
|
|
# if (field1 = w or d) |
736
|
|
|
|
|
|
|
# add [w ... [f1]] |
737
|
|
|
|
|
|
|
# done |
738
|
|
|
|
|
|
|
# else |
739
|
|
|
|
|
|
|
# add [w,d] |
740
|
|
|
|
|
|
|
# field0 = h |
741
|
13
|
100
|
|
|
|
17
|
if ($f1 <= 3) { |
742
|
7
|
|
|
|
|
15
|
push(@set, [ @delta[$f0..$f1] ]); |
743
|
7
|
|
|
|
|
8
|
$f0 = 7; |
744
|
|
|
|
|
|
|
} else { |
745
|
6
|
|
|
|
|
13
|
push(@set, [ @delta[$f0..3] ]); |
746
|
6
|
|
|
|
|
7
|
$f0 = 4; |
747
|
|
|
|
|
|
|
} |
748
|
|
|
|
|
|
|
} |
749
|
|
|
|
|
|
|
|
750
|
15
|
100
|
|
|
|
35
|
if ($f0 <= 6) { |
751
|
6
|
|
|
|
|
15
|
push(@set, [ @delta[$f0..$f1] ]); |
752
|
|
|
|
|
|
|
} |
753
|
|
|
|
|
|
|
} |
754
|
|
|
|
|
|
|
|
755
|
|
|
|
|
|
|
# If we're not forcing signs, remove signs from all fields |
756
|
|
|
|
|
|
|
# except the first in each set. |
757
|
|
|
|
|
|
|
|
758
|
22
|
|
|
|
|
26
|
my @ret; |
759
|
|
|
|
|
|
|
|
760
|
22
|
|
|
|
|
26
|
foreach my $set (@set) { |
761
|
44
|
|
|
|
|
75
|
my @f = @$set; |
762
|
|
|
|
|
|
|
|
763
|
44
|
100
|
66
|
|
|
94
|
if (defined($sign) && $sign eq "+") { |
764
|
16
|
|
|
|
|
28
|
push(@ret,@f); |
765
|
|
|
|
|
|
|
} else { |
766
|
28
|
|
|
|
|
38
|
push(@ret,shift(@f)); |
767
|
28
|
|
|
|
|
36
|
foreach my $f (@f) { |
768
|
26
|
|
|
|
|
59
|
$f =~ s/[-+]//; |
769
|
26
|
|
|
|
|
47
|
push(@ret,$f); |
770
|
|
|
|
|
|
|
} |
771
|
|
|
|
|
|
|
} |
772
|
|
|
|
|
|
|
} |
773
|
|
|
|
|
|
|
|
774
|
|
|
|
|
|
|
# Width/pad |
775
|
|
|
|
|
|
|
|
776
|
22
|
|
|
|
|
44
|
my $ret = join(':',@ret); |
777
|
22
|
100
|
100
|
|
|
47
|
if ($width && length($ret) < $width) { |
778
|
3
|
100
|
100
|
|
|
10
|
if (defined $pad && $pad eq ">") { |
779
|
1
|
|
|
|
|
3
|
$ret .= ' 'x($width-length($ret)); |
780
|
|
|
|
|
|
|
} else { |
781
|
2
|
|
|
|
|
5
|
$ret = ' 'x($width-length($ret)) . $ret; |
782
|
|
|
|
|
|
|
} |
783
|
|
|
|
|
|
|
} |
784
|
|
|
|
|
|
|
|
785
|
22
|
|
|
|
|
123
|
return $ret; |
786
|
|
|
|
|
|
|
} |
787
|
|
|
|
|
|
|
|
788
|
|
|
|
|
|
|
sub _printf_field { |
789
|
2521
|
|
|
2521
|
|
6657
|
my($self,$sign,$pad,$width,$precision,$field,@field) = @_; |
790
|
|
|
|
|
|
|
|
791
|
2521
|
|
|
|
|
5454
|
my $val = $self->_printf_field_val($field,@field); |
792
|
2521
|
100
|
|
|
|
5045
|
$pad = "<" if (! defined($pad)); |
793
|
|
|
|
|
|
|
|
794
|
|
|
|
|
|
|
# Strip off the sign. |
795
|
|
|
|
|
|
|
|
796
|
2521
|
|
|
|
|
3274
|
my $s = ''; |
797
|
|
|
|
|
|
|
|
798
|
2521
|
100
|
|
|
|
5678
|
if ($val < 0) { |
|
|
100
|
|
|
|
|
|
799
|
66
|
|
|
|
|
98
|
$s = "-"; |
800
|
66
|
|
|
|
|
89
|
$val *= -1; |
801
|
|
|
|
|
|
|
} elsif ($sign) { |
802
|
16
|
|
|
|
|
23
|
$s = "+"; |
803
|
|
|
|
|
|
|
} |
804
|
|
|
|
|
|
|
|
805
|
|
|
|
|
|
|
# Handle the precision. |
806
|
|
|
|
|
|
|
|
807
|
2521
|
100
|
|
|
|
5331
|
if (defined($precision)) { |
|
|
50
|
|
|
|
|
|
808
|
222
|
|
|
|
|
886
|
$val = sprintf("%.${precision}f",$val); |
809
|
|
|
|
|
|
|
|
810
|
|
|
|
|
|
|
} elsif (defined($width)) { |
811
|
0
|
|
|
|
|
0
|
my $i = $s . int($val) . '.'; |
812
|
0
|
0
|
|
|
|
0
|
if (length($i) < $width) { |
813
|
0
|
|
|
|
|
0
|
$precision = $width-length($i); |
814
|
0
|
|
|
|
|
0
|
$val = sprintf("%.${precision}f",$val); |
815
|
|
|
|
|
|
|
} |
816
|
|
|
|
|
|
|
} |
817
|
|
|
|
|
|
|
|
818
|
|
|
|
|
|
|
# Handle padding. |
819
|
|
|
|
|
|
|
|
820
|
2521
|
100
|
|
|
|
3874
|
if ($width) { |
821
|
38
|
100
|
|
|
|
62
|
if ($pad eq ">") { |
|
|
100
|
|
|
|
|
|
822
|
8
|
|
|
|
|
11
|
$val = "$s$val"; |
823
|
8
|
100
|
|
|
|
18
|
my $pad = ($width > length($val) ? $width - length($val) : 0); |
824
|
8
|
|
|
|
|
38
|
$val .= ' 'x$pad; |
825
|
|
|
|
|
|
|
|
826
|
|
|
|
|
|
|
} elsif ($pad eq "<") { |
827
|
15
|
|
|
|
|
19
|
$val = "$s$val"; |
828
|
15
|
100
|
|
|
|
29
|
my $pad = ($width > length($val) ? $width - length($val) : 0); |
829
|
15
|
|
|
|
|
23
|
$val = ' 'x$pad . $val; |
830
|
|
|
|
|
|
|
|
831
|
|
|
|
|
|
|
} else { |
832
|
15
|
100
|
|
|
|
31
|
my $pad = ($width > length($val)-length($s) ? |
833
|
|
|
|
|
|
|
$width - length($val) - length($s): 0); |
834
|
15
|
|
|
|
|
23
|
$val = $s . '0'x$pad . $val; |
835
|
|
|
|
|
|
|
} |
836
|
|
|
|
|
|
|
} else { |
837
|
2483
|
|
|
|
|
4826
|
$val = "$s$val"; |
838
|
|
|
|
|
|
|
} |
839
|
|
|
|
|
|
|
|
840
|
2521
|
|
|
|
|
9167
|
return $val; |
841
|
|
|
|
|
|
|
} |
842
|
|
|
|
|
|
|
|
843
|
|
|
|
|
|
|
# $$self{'data'}{'f'}{X}{Y} is the value of field X expressed in terms of Y. |
844
|
|
|
|
|
|
|
# |
845
|
|
|
|
|
|
|
sub _printf_field_val { |
846
|
2521
|
|
|
2521
|
|
5708
|
my($self,$field,@field) = @_; |
847
|
|
|
|
|
|
|
|
848
|
2521
|
50
|
66
|
|
|
9811
|
if (! exists $$self{'data'}{'f'}{'y'} && |
849
|
|
|
|
|
|
|
! exists $$self{'data'}{'f'}{'y'}{'y'}) { |
850
|
|
|
|
|
|
|
|
851
|
1516
|
|
|
|
|
2231
|
my($yv,$Mv,$wv,$dv,$hv,$mv,$sv) = map { $_*1 } @{ $$self{'data'}{'delta'} }; |
|
10612
|
|
|
|
|
14978
|
|
|
1516
|
|
|
|
|
3751
|
|
852
|
1516
|
|
|
|
|
3360
|
$$self{'data'}{'f'}{'y'}{'y'} = $yv; |
853
|
1516
|
|
|
|
|
3070
|
$$self{'data'}{'f'}{'M'}{'M'} = $Mv; |
854
|
1516
|
|
|
|
|
2999
|
$$self{'data'}{'f'}{'w'}{'w'} = $wv; |
855
|
1516
|
|
|
|
|
2990
|
$$self{'data'}{'f'}{'d'}{'d'} = $dv; |
856
|
1516
|
|
|
|
|
2945
|
$$self{'data'}{'f'}{'h'}{'h'} = $hv; |
857
|
1516
|
|
|
|
|
2829
|
$$self{'data'}{'f'}{'m'}{'m'} = $mv; |
858
|
1516
|
|
|
|
|
3313
|
$$self{'data'}{'f'}{'s'}{'s'} = $sv; |
859
|
|
|
|
|
|
|
} |
860
|
|
|
|
|
|
|
|
861
|
|
|
|
|
|
|
# A single field |
862
|
|
|
|
|
|
|
|
863
|
2521
|
100
|
|
|
|
4820
|
if (! @field) { |
864
|
18
|
|
|
|
|
33
|
return $$self{'data'}{'f'}{$field}{$field}; |
865
|
|
|
|
|
|
|
} |
866
|
|
|
|
|
|
|
|
867
|
|
|
|
|
|
|
# Find the length of 1 unit of each field in terms of seconds. |
868
|
|
|
|
|
|
|
|
869
|
2503
|
100
|
|
|
|
5556
|
if (! exists $$self{'data'}{'flen'}{'s'}) { |
870
|
1510
|
|
|
|
|
2582
|
my $mode = $$self{'data'}{'mode'}; |
871
|
1510
|
|
|
|
|
4213
|
my $dmb = $self->base(); |
872
|
|
|
|
|
|
|
$$self{'data'}{'flen'} = { 's' => 1, |
873
|
|
|
|
|
|
|
'm' => 60, |
874
|
|
|
|
|
|
|
'h' => 3600, |
875
|
|
|
|
|
|
|
'd' => $$dmb{'data'}{'len'}{$mode}{'dl'}, |
876
|
|
|
|
|
|
|
'w' => $$dmb{'data'}{'len'}{$mode}{'wl'}, |
877
|
|
|
|
|
|
|
'M' => $$dmb{'data'}{'len'}{$mode}{'ml'}, |
878
|
1510
|
|
|
|
|
9186
|
'y' => $$dmb{'data'}{'len'}{$mode}{'yl'}, |
879
|
|
|
|
|
|
|
}; |
880
|
|
|
|
|
|
|
} |
881
|
|
|
|
|
|
|
|
882
|
|
|
|
|
|
|
# Calculate the value for each field. |
883
|
|
|
|
|
|
|
|
884
|
2503
|
|
|
|
|
3821
|
my $val = 0; |
885
|
2503
|
|
|
|
|
3869
|
foreach my $f (@field) { |
886
|
|
|
|
|
|
|
|
887
|
|
|
|
|
|
|
# We want the value of $f expressed in terms of $field |
888
|
|
|
|
|
|
|
|
889
|
16841
|
100
|
|
|
|
28127
|
if (! exists $$self{'data'}{'f'}{$f}{$field}) { |
890
|
|
|
|
|
|
|
|
891
|
|
|
|
|
|
|
# Get the value of $f expressed in seconds |
892
|
|
|
|
|
|
|
|
893
|
9372
|
100
|
|
|
|
14197
|
if (! exists $$self{'data'}{'f'}{$f}{'s'}) { |
894
|
|
|
|
|
|
|
$$self{'data'}{'f'}{$f}{'s'} = |
895
|
9033
|
|
|
|
|
14818
|
$$self{'data'}{'f'}{$f}{$f} * $$self{'data'}{'flen'}{$f}; |
896
|
|
|
|
|
|
|
} |
897
|
|
|
|
|
|
|
|
898
|
|
|
|
|
|
|
# Get the value of $f expressed in terms of $field |
899
|
|
|
|
|
|
|
|
900
|
|
|
|
|
|
|
$$self{'data'}{'f'}{$f}{$field} = |
901
|
9372
|
|
|
|
|
16334
|
$$self{'data'}{'f'}{$f}{'s'} / $$self{'data'}{'flen'}{$field}; |
902
|
|
|
|
|
|
|
} |
903
|
|
|
|
|
|
|
|
904
|
16841
|
|
|
|
|
23508
|
$val += $$self{'data'}{'f'}{$f}{$field}; |
905
|
|
|
|
|
|
|
} |
906
|
|
|
|
|
|
|
|
907
|
2503
|
|
|
|
|
4768
|
return $val; |
908
|
|
|
|
|
|
|
} |
909
|
|
|
|
|
|
|
|
910
|
|
|
|
|
|
|
sub type { |
911
|
54
|
|
|
54
|
1
|
3134
|
my($self,$op) = @_; |
912
|
54
|
|
|
|
|
79
|
$op = lc($op); |
913
|
|
|
|
|
|
|
|
914
|
54
|
100
|
100
|
|
|
133
|
if ($op eq 'business' || |
915
|
|
|
|
|
|
|
$op eq 'standard') { |
916
|
33
|
100
|
|
|
|
93
|
return ($$self{'data'}{'mode'} eq $op ? 1 : 0); |
917
|
|
|
|
|
|
|
} |
918
|
|
|
|
|
|
|
|
919
|
21
|
100
|
|
|
|
62
|
return ($$self{'data'}{'type'} eq $op ? 1 : 0); |
920
|
|
|
|
|
|
|
} |
921
|
|
|
|
|
|
|
|
922
|
|
|
|
|
|
|
sub calc { |
923
|
29
|
|
|
29
|
1
|
123
|
my($self,$obj,@args) = @_; |
924
|
29
|
50
|
|
|
|
67
|
if ($$self{'err'}) { |
925
|
0
|
|
|
|
|
0
|
$$self{'err'} = "[calc] First object invalid (delta)"; |
926
|
0
|
|
|
|
|
0
|
return undef; |
927
|
|
|
|
|
|
|
} |
928
|
|
|
|
|
|
|
|
929
|
29
|
50
|
|
|
|
113
|
if (ref($obj) eq 'Date::Manip::Date') { |
|
|
50
|
|
|
|
|
|
930
|
0
|
0
|
|
|
|
0
|
if ($$obj{'err'}) { |
931
|
0
|
|
|
|
|
0
|
$$self{'err'} = "[calc] Second object invalid (date)"; |
932
|
0
|
|
|
|
|
0
|
return undef; |
933
|
|
|
|
|
|
|
} |
934
|
0
|
|
|
|
|
0
|
return $obj->calc($self,@args); |
935
|
|
|
|
|
|
|
|
936
|
|
|
|
|
|
|
} elsif (ref($obj) eq 'Date::Manip::Delta') { |
937
|
29
|
50
|
|
|
|
64
|
if ($$obj{'err'}) { |
938
|
0
|
|
|
|
|
0
|
$$self{'err'} = "[calc] Second object invalid (delta)"; |
939
|
0
|
|
|
|
|
0
|
return undef; |
940
|
|
|
|
|
|
|
} |
941
|
29
|
|
|
|
|
79
|
return $self->_calc_delta_delta($obj,@args); |
942
|
|
|
|
|
|
|
|
943
|
|
|
|
|
|
|
} else { |
944
|
0
|
|
|
|
|
0
|
$$self{'err'} = "[calc] Second object must be a Date/Delta object"; |
945
|
0
|
|
|
|
|
0
|
return undef; |
946
|
|
|
|
|
|
|
} |
947
|
|
|
|
|
|
|
} |
948
|
|
|
|
|
|
|
|
949
|
|
|
|
|
|
|
sub __type_max { |
950
|
29
|
|
|
29
|
|
64
|
my($type1,$type2) = @_; |
951
|
29
|
100
|
|
|
|
72
|
return $type1 if ($type1 eq $type2); |
952
|
2
|
|
|
|
|
4
|
foreach my $type ('estimate','approx','semi') { |
953
|
6
|
100
|
66
|
|
|
18
|
return $type if ($type1 eq $type || $type2 eq $type); |
954
|
|
|
|
|
|
|
} |
955
|
0
|
|
|
|
|
0
|
return 'exact'; |
956
|
|
|
|
|
|
|
} |
957
|
|
|
|
|
|
|
|
958
|
|
|
|
|
|
|
sub _calc_delta_delta { |
959
|
29
|
|
|
29
|
|
45
|
my($self,$delta,@args) = @_; |
960
|
29
|
|
|
|
|
45
|
my $dmt = $$self{'tz'}; |
961
|
29
|
|
|
|
|
44
|
my $dmb = $$dmt{'base'}; |
962
|
29
|
|
|
|
|
108
|
my $ret = $self->new_delta; |
963
|
|
|
|
|
|
|
|
964
|
29
|
|
|
|
|
43
|
my($subtract,$no_normalize); |
965
|
29
|
50
|
|
|
|
112
|
if (@args > 2) { |
966
|
0
|
|
|
|
|
0
|
$$ret{'err'} = "Unknown args in calc"; |
967
|
0
|
|
|
|
|
0
|
return $ret; |
968
|
|
|
|
|
|
|
} |
969
|
|
|
|
|
|
|
|
970
|
29
|
50
|
|
|
|
86
|
if (@args == 2) { |
|
|
100
|
|
|
|
|
|
971
|
0
|
|
|
|
|
0
|
($subtract,$no_normalize) = @args; |
972
|
|
|
|
|
|
|
} elsif (@args == 1) { |
973
|
4
|
50
|
|
|
|
14
|
if ($args[0] eq 'nonormalize') { |
974
|
0
|
|
|
|
|
0
|
$subtract = 0; |
975
|
0
|
|
|
|
|
0
|
$no_normalize = 1; |
976
|
|
|
|
|
|
|
} else { |
977
|
4
|
|
|
|
|
8
|
$subtract = $args[0]; |
978
|
4
|
|
|
|
|
7
|
$no_normalize = 0; |
979
|
|
|
|
|
|
|
} |
980
|
|
|
|
|
|
|
} else { |
981
|
25
|
|
|
|
|
40
|
$subtract = 0; |
982
|
25
|
|
|
|
|
32
|
$no_normalize = 0; |
983
|
|
|
|
|
|
|
} |
984
|
|
|
|
|
|
|
|
985
|
29
|
50
|
|
|
|
79
|
if ($$self{'data'}{'mode'} ne $$delta{'data'}{'mode'}) { |
986
|
0
|
|
|
|
|
0
|
$$ret{'err'} = "[calc] Delta/delta calculation objects must be of " . |
987
|
|
|
|
|
|
|
'the same mode'; |
988
|
0
|
|
|
|
|
0
|
return $ret; |
989
|
|
|
|
|
|
|
} |
990
|
|
|
|
|
|
|
|
991
|
29
|
|
|
|
|
38
|
my ($err,@delta); |
992
|
29
|
|
|
|
|
70
|
for (my $i=0; $i<7; $i++) { |
993
|
203
|
100
|
|
|
|
241
|
if ($subtract) { |
994
|
28
|
|
|
|
|
49
|
$delta[$i] = $$self{'data'}{'delta'}[$i] - $$delta{'data'}{'delta'}[$i]; |
995
|
|
|
|
|
|
|
} else { |
996
|
175
|
|
|
|
|
354
|
$delta[$i] = $$self{'data'}{'delta'}[$i] + $$delta{'data'}{'delta'}[$i]; |
997
|
|
|
|
|
|
|
} |
998
|
|
|
|
|
|
|
} |
999
|
|
|
|
|
|
|
|
1000
|
|
|
|
|
|
|
my $type = __type_max($$self{'data'}{'type'}, |
1001
|
29
|
|
|
|
|
74
|
$$delta{'data'}{'type'}); |
1002
|
|
|
|
|
|
|
my %o = ( 'source' => 'delta', |
1003
|
|
|
|
|
|
|
'nonorm' => $no_normalize, |
1004
|
|
|
|
|
|
|
'sign' => -1, |
1005
|
|
|
|
|
|
|
'type' => $type, |
1006
|
29
|
|
|
|
|
109
|
'mode' => $$self{'data'}{'mode'}, |
1007
|
|
|
|
|
|
|
); |
1008
|
|
|
|
|
|
|
|
1009
|
29
|
|
|
|
|
98
|
($err,@delta) = $dmb->_delta_fields( \%o, [@delta]); |
1010
|
|
|
|
|
|
|
|
1011
|
29
|
|
|
|
|
70
|
$$ret{'data'}{'in'} = ''; |
1012
|
29
|
|
|
|
|
76
|
$$ret{'data'}{'delta'} = [@delta]; |
1013
|
29
|
|
|
|
|
51
|
$$ret{'data'}{'mode'} = $$self{'data'}{'mode'}; |
1014
|
29
|
|
|
|
|
45
|
$$ret{'data'}{'gotmode'} = 1; |
1015
|
29
|
|
|
|
|
50
|
$$ret{'data'}{'type'} = $type; |
1016
|
29
|
|
|
|
|
44
|
$$ret{'data'}{'type_from'} = 'det'; |
1017
|
29
|
|
|
|
|
43
|
$$ret{'data'}{'length'} = 'unknown'; |
1018
|
29
|
|
|
|
|
41
|
$$ret{'data'}{'normalized'} = 1-$no_normalize; |
1019
|
|
|
|
|
|
|
|
1020
|
29
|
|
|
|
|
133
|
return $ret; |
1021
|
|
|
|
|
|
|
} |
1022
|
|
|
|
|
|
|
|
1023
|
|
|
|
|
|
|
sub convert { |
1024
|
62
|
|
|
62
|
1
|
195
|
my($self,$to) = @_; |
1025
|
|
|
|
|
|
|
|
1026
|
62
|
|
|
|
|
178
|
my %mode_val = ( 'exact' => 0, |
1027
|
|
|
|
|
|
|
'semi' => 1, |
1028
|
|
|
|
|
|
|
'approx' => 2, |
1029
|
|
|
|
|
|
|
'estimated' => 3, |
1030
|
|
|
|
|
|
|
); |
1031
|
|
|
|
|
|
|
|
1032
|
62
|
|
|
|
|
85
|
my $from = $$self{'data'}{'type'}; |
1033
|
62
|
|
|
|
|
78
|
my $from_val = $mode_val{$from}; |
1034
|
62
|
|
|
|
|
77
|
my $to_val = $mode_val{$to}; |
1035
|
|
|
|
|
|
|
|
1036
|
62
|
100
|
|
|
|
124
|
return if ($from_val == $to_val); |
1037
|
|
|
|
|
|
|
|
1038
|
|
|
|
|
|
|
# |
1039
|
|
|
|
|
|
|
# Converting from exact to less exact |
1040
|
|
|
|
|
|
|
# |
1041
|
|
|
|
|
|
|
|
1042
|
43
|
100
|
|
|
|
77
|
if ($from_val < $to_val) { |
1043
|
|
|
|
|
|
|
|
1044
|
35
|
|
|
|
|
119
|
$self->set( { 'nonorm' => 0, |
1045
|
|
|
|
|
|
|
'type' => $to } ); |
1046
|
35
|
|
|
|
|
109
|
return; |
1047
|
|
|
|
|
|
|
} |
1048
|
|
|
|
|
|
|
|
1049
|
|
|
|
|
|
|
# |
1050
|
|
|
|
|
|
|
# Converting from less exact to more exact |
1051
|
|
|
|
|
|
|
# *** DEPRECATE *** 7.00 |
1052
|
|
|
|
|
|
|
# |
1053
|
|
|
|
|
|
|
|
1054
|
8
|
|
|
|
|
9
|
my @fields; |
1055
|
|
|
|
|
|
|
{ |
1056
|
168
|
|
|
168
|
|
1477
|
no integer; |
|
168
|
|
|
|
|
396
|
|
|
168
|
|
|
|
|
1416
|
|
|
8
|
|
|
|
|
9
|
|
1057
|
|
|
|
|
|
|
|
1058
|
8
|
|
|
|
|
29
|
my $dmb = $self->base(); |
1059
|
8
|
|
|
|
|
16
|
my $mode= $$self{'data'}{'mode'}; |
1060
|
8
|
|
|
|
|
13
|
my $yl = $$dmb{'data'}{'len'}{$mode}{'yl'}; |
1061
|
8
|
|
|
|
|
13
|
my $ml = $$dmb{'data'}{'len'}{$mode}{'ml'}; |
1062
|
8
|
|
|
|
|
15
|
my $wl = $$dmb{'data'}{'len'}{$mode}{'wl'}; |
1063
|
8
|
|
|
|
|
10
|
my $dl = $$dmb{'data'}{'len'}{$mode}{'dl'}; |
1064
|
|
|
|
|
|
|
|
1065
|
|
|
|
|
|
|
# Convert it to seconds |
1066
|
|
|
|
|
|
|
|
1067
|
8
|
|
|
|
|
10
|
my($y,$m,$w,$d,$h,$mn,$s) = @{ $$self{'data'}{'delta'} }; |
|
8
|
|
|
|
|
20
|
|
1068
|
8
|
|
|
|
|
20
|
$s += $y*$yl + $m*$ml + $w*$wl + $d*$dl + $h*3600 + $mn*60; |
1069
|
|
|
|
|
|
|
|
1070
|
8
|
|
|
|
|
16
|
@fields = (0,0,0,0,0,0,$s); |
1071
|
|
|
|
|
|
|
|
1072
|
8
|
100
|
|
|
|
14
|
if ($mode eq 'business') { |
1073
|
|
|
|
|
|
|
|
1074
|
4
|
50
|
66
|
|
|
28
|
if ($to eq 'estimated') { |
|
|
100
|
|
|
|
|
|
1075
|
0
|
|
|
|
|
0
|
@fields = $dmb->_normalize_bus_est(@fields); |
1076
|
|
|
|
|
|
|
|
1077
|
|
|
|
|
|
|
} elsif ($to eq 'approx' || |
1078
|
|
|
|
|
|
|
$to eq 'semi') { |
1079
|
1
|
|
|
|
|
3
|
@fields = $dmb->_normalize_bus_approx(@fields); |
1080
|
|
|
|
|
|
|
|
1081
|
|
|
|
|
|
|
} else { |
1082
|
3
|
|
|
|
|
10
|
@fields = $dmb->_normalize_bus_exact(@fields); |
1083
|
|
|
|
|
|
|
} |
1084
|
|
|
|
|
|
|
|
1085
|
|
|
|
|
|
|
} else { |
1086
|
|
|
|
|
|
|
|
1087
|
4
|
50
|
66
|
|
|
17
|
if ($to eq 'estimated') { |
|
|
100
|
|
|
|
|
|
1088
|
0
|
|
|
|
|
0
|
@fields = $dmb->_normalize_est(@fields); |
1089
|
|
|
|
|
|
|
|
1090
|
|
|
|
|
|
|
} elsif ($to eq 'approx' || |
1091
|
|
|
|
|
|
|
$to eq 'semi') { |
1092
|
1
|
|
|
|
|
4
|
@fields = $dmb->_normalize_approx(@fields); |
1093
|
|
|
|
|
|
|
|
1094
|
|
|
|
|
|
|
} else { |
1095
|
3
|
|
|
|
|
10
|
@fields = $dmb->_normalize_exact(@fields); |
1096
|
|
|
|
|
|
|
} |
1097
|
|
|
|
|
|
|
|
1098
|
|
|
|
|
|
|
} |
1099
|
|
|
|
|
|
|
} |
1100
|
|
|
|
|
|
|
|
1101
|
8
|
|
|
|
|
24
|
$$self{'data'}{'delta'} = [ @fields ]; |
1102
|
8
|
|
|
|
|
12
|
$$self{'data'}{'gotmode'} = 1; |
1103
|
8
|
|
|
|
|
13
|
$$self{'data'}{'type'} = $to; |
1104
|
8
|
|
|
|
|
13
|
$$self{'data'}{'type_from'} = 'opt'; |
1105
|
8
|
|
|
|
|
11
|
$$self{'data'}{'normalized'} = 1; |
1106
|
8
|
|
|
|
|
21
|
$$self{'data'}{'length'} = 'unknown'; |
1107
|
|
|
|
|
|
|
} |
1108
|
|
|
|
|
|
|
|
1109
|
|
|
|
|
|
|
sub cmp { |
1110
|
3
|
|
|
3
|
1
|
15
|
my($self,$delta) = @_; |
1111
|
|
|
|
|
|
|
|
1112
|
3
|
50
|
|
|
|
8
|
if ($$self{'err'}) { |
1113
|
0
|
|
|
|
|
0
|
carp "WARNING: [cmp] Arguments must be valid deltas: delta1"; |
1114
|
0
|
|
|
|
|
0
|
return undef; |
1115
|
|
|
|
|
|
|
} |
1116
|
|
|
|
|
|
|
|
1117
|
3
|
50
|
|
|
|
8
|
if (! ref($delta) eq 'Date::Manip::Delta') { |
1118
|
0
|
|
|
|
|
0
|
carp "WARNING: [cmp] Argument must be a Date::Manip::Delta object"; |
1119
|
0
|
|
|
|
|
0
|
return undef; |
1120
|
|
|
|
|
|
|
} |
1121
|
3
|
50
|
|
|
|
6
|
if ($$delta{'err'}) { |
1122
|
0
|
|
|
|
|
0
|
carp "WARNING: [cmp] Arguments must be valid deltas: delta2"; |
1123
|
0
|
|
|
|
|
0
|
return undef; |
1124
|
|
|
|
|
|
|
} |
1125
|
|
|
|
|
|
|
|
1126
|
3
|
50
|
|
|
|
6
|
if ($$self{'data'}{'mode'} ne $$delta{'data'}{'mode'}) { |
1127
|
0
|
|
|
|
|
0
|
carp "WARNING: [cmp] Deltas must both be business or standard"; |
1128
|
0
|
|
|
|
|
0
|
return undef; |
1129
|
|
|
|
|
|
|
} |
1130
|
|
|
|
|
|
|
|
1131
|
3
|
|
|
|
|
5
|
my $mode = $$self{'data'}{'mode'}; |
1132
|
3
|
|
|
|
|
16
|
my $dmb = $self->base(); |
1133
|
3
|
|
|
|
|
7
|
my $yl = $$dmb{'data'}{'len'}{$mode}{'yl'}; |
1134
|
3
|
|
|
|
|
4
|
my $ml = $$dmb{'data'}{'len'}{$mode}{'ml'}; |
1135
|
3
|
|
|
|
|
5
|
my $wl = $$dmb{'data'}{'len'}{$mode}{'wl'}; |
1136
|
3
|
|
|
|
|
5
|
my $dl = $$dmb{'data'}{'len'}{$mode}{'dl'}; |
1137
|
|
|
|
|
|
|
|
1138
|
3
|
50
|
|
|
|
7
|
if ($$self{'data'}{'length'} eq 'unknown') { |
1139
|
3
|
|
|
|
|
3
|
my($y,$m,$w,$d,$h,$mn,$s) = @{ $$self{'data'}{'delta'} }; |
|
3
|
|
|
|
|
6
|
|
1140
|
|
|
|
|
|
|
|
1141
|
168
|
|
|
168
|
|
74392
|
no integer; |
|
168
|
|
|
|
|
357
|
|
|
168
|
|
|
|
|
764
|
|
1142
|
3
|
|
|
|
|
8
|
$$self{'data'}{'length'} = int($y*$yl + $m*$ml + $w*$wl + |
1143
|
|
|
|
|
|
|
$d*$dl + $h*3600 + $mn*60 + $s); |
1144
|
|
|
|
|
|
|
} |
1145
|
|
|
|
|
|
|
|
1146
|
3
|
50
|
|
|
|
29
|
if ($$delta{'data'}{'length'} eq 'unknown') { |
1147
|
3
|
|
|
|
|
5
|
my($y,$m,$w,$d,$h,$mn,$s) = @{ $$delta{'data'}{'delta'} }; |
|
3
|
|
|
|
|
8
|
|
1148
|
|
|
|
|
|
|
|
1149
|
168
|
|
|
168
|
|
16251
|
no integer; |
|
168
|
|
|
|
|
379
|
|
|
168
|
|
|
|
|
700
|
|
1150
|
3
|
|
|
|
|
6
|
$$delta{'data'}{'length'} = int($y*$yl + $m*$ml + $w*$wl + |
1151
|
|
|
|
|
|
|
$d*$dl + $h*3600 + $mn*60 + $s); |
1152
|
|
|
|
|
|
|
} |
1153
|
|
|
|
|
|
|
|
1154
|
3
|
|
|
|
|
12
|
return ($$self{'data'}{'length'} <=> $$delta{'data'}{'length'}); |
1155
|
|
|
|
|
|
|
} |
1156
|
|
|
|
|
|
|
|
1157
|
|
|
|
|
|
|
1; |
1158
|
|
|
|
|
|
|
# Local Variables: |
1159
|
|
|
|
|
|
|
# mode: cperl |
1160
|
|
|
|
|
|
|
# indent-tabs-mode: nil |
1161
|
|
|
|
|
|
|
# cperl-indent-level: 3 |
1162
|
|
|
|
|
|
|
# cperl-continued-statement-offset: 2 |
1163
|
|
|
|
|
|
|
# cperl-continued-brace-offset: 0 |
1164
|
|
|
|
|
|
|
# cperl-brace-offset: 0 |
1165
|
|
|
|
|
|
|
# cperl-brace-imaginary-offset: 0 |
1166
|
|
|
|
|
|
|
# cperl-label-offset: 0 |
1167
|
|
|
|
|
|
|
# End: |