File Coverage

blib/lib/Statistics/Standard_Normal.pm
Criterion Covered Total %
statement 37 37 100.0
branch 18 22 81.8
condition 3 6 50.0
subroutine 6 6 100.0
pod 2 2 100.0
total 66 73 90.4


line stmt bran cond sub pod time code
1             #!/usr/local/bin/perl
2              
3 3     3   36364 use strict;
  3         6  
  3         125  
4 3     3   17 use warnings;
  3         5  
  3         333  
5              
6             package Statistics::Standard_Normal;
7              
8             our ($VERSION) = '1.00';
9              
10 3     3   29 use Exporter qw(import);
  3         6  
  3         1821  
11             our (@EXPORT_OK) = qw(z_to_pct pct_to_z);
12              
13             my @_Pctile_Z_map =
14             map { { pct => $_->[0], Z => $_->[1] } } (
15             [ 0, 0 ],
16             [ 0.5, 0.01253347 ],
17             [ 1, 0.02506891 ],
18             [ 1.5, 0.03760829 ],
19             [ 2, 0.05015358 ],
20             [ 2.5, 0.06270678 ],
21             [ 3, 0.07526986 ],
22             [ 3.5, 0.08784484 ],
23             [ 4, 0.1004337 ],
24             [ 4.5, 0.1130385 ],
25             [ 5, 0.1256613 ],
26             [ 5.5, 0.1383042 ],
27             [ 6, 0.1509692 ],
28             [ 6.5, 0.1636585 ],
29             [ 7, 0.1763742 ],
30             [ 7.5, 0.1891184 ],
31             [ 8, 0.2018935 ],
32             [ 8.5, 0.2147016 ],
33             [ 9, 0.227545 ],
34             [ 9.5, 0.240426 ],
35             [ 10, 0.2533471 ],
36             [ 10.5, 0.2663106 ],
37             [ 11, 0.279319 ],
38             [ 11.5, 0.2923749 ],
39             [ 12, 0.3054808 ],
40             [ 12.5, 0.3186394 ],
41             [ 13, 0.3318533 ],
42             [ 13.5, 0.3451255 ],
43             [ 14, 0.3584588 ],
44             [ 14.5, 0.3718561 ],
45             [ 15, 0.3853205 ],
46             [ 15.5, 0.3988551 ],
47             [ 16, 0.4124631 ],
48             [ 16.5, 0.426148 ],
49             [ 17, 0.4399132 ],
50             [ 17.5, 0.4537622 ],
51             [ 18, 0.4676988 ],
52             [ 18.5, 0.4817268 ],
53             [ 19, 0.4958503 ],
54             [ 19.5, 0.5100735 ],
55             [ 20, 0.5244005 ],
56             [ 20.5, 0.538836 ],
57             [ 21, 0.5533847 ],
58             [ 21.5, 0.5680515 ],
59             [ 22, 0.5828415 ],
60             [ 22.5, 0.5977601 ],
61             [ 23, 0.612813 ],
62             [ 23.5, 0.628006 ],
63             [ 24, 0.6433454 ],
64             [ 24.5, 0.6588377 ],
65             [ 25, 0.6744898 ],
66             [ 25.5, 0.6903088 ],
67             [ 26, 0.7063026 ],
68             [ 26.5, 0.7224791 ],
69             [ 27, 0.7388468 ],
70             [ 27.5, 0.755415 ],
71             [ 28, 0.7721932 ],
72             [ 28.5, 0.7891917 ],
73             [ 29, 0.8064212 ],
74             [ 29.5, 0.8238936 ],
75             [ 30, 0.8416212 ],
76             [ 30.5, 0.8596174 ],
77             [ 31, 0.8778963 ],
78             [ 31.5, 0.8964734 ],
79             [ 32, 0.9153651 ],
80             [ 32.5, 0.9345893 ],
81             [ 33, 0.9541653 ],
82             [ 33.5, 0.9741139 ],
83             [ 34, 0.9944579 ],
84             [ 34.5, 1.015222 ],
85             [ 35, 1.036433 ],
86             [ 35.5, 1.058122 ],
87             [ 36, 1.080319 ],
88             [ 36.5, 1.103063 ],
89             [ 37, 1.126391 ],
90             [ 37.5, 1.150349 ],
91             [ 38, 1.174987 ],
92             [ 38.5, 1.200359 ],
93             [ 39, 1.226528 ],
94             [ 39.5, 1.253565 ],
95             [ 40, 1.281552 ],
96             [ 40.5, 1.310579 ],
97             [ 41, 1.340755 ],
98             [ 41.5, 1.372204 ],
99             [ 42, 1.405072 ],
100             [ 42.5, 1.439531 ],
101             [ 43, 1.475791 ],
102             [ 43.5, 1.514102 ],
103             [ 44, 1.554774 ],
104             [ 44.5, 1.598193 ],
105             [ 45, 1.644854 ],
106             [ 45.5, 1.695398 ],
107             [ 46, 1.750686 ],
108             [ 46.5, 1.811911 ],
109             [ 47, 1.880794 ],
110             [ 47.5, 1.959964 ],
111             [ 48, 2.053749 ],
112             [ 48.5, 2.17009 ],
113             [ 49, 2.326348 ],
114             [ 49.5, 2.575829 ],
115             [ 49.9, 3.090232 ],
116             [ 49.95, 3.290527 ],
117             [ 49.99, 3.719016 ],
118             );
119              
120             sub _transform_score {
121 30     30   39 my ( $qty, $stype ) = @_;
122 30 50 33     138 return unless defined $qty and defined $stype;
123 30 50       78 my $dtype =
    100          
124             $stype eq 'Z'
125             ? 'pct'
126             : ( $stype eq 'pct' ? 'Z' : undef );
127 30 50       52 return unless defined $dtype;
128 30         37 my $match = abs($qty);
129              
130 30 100       124 if ( $match <= $_Pctile_Z_map[0]->{$stype} ) {
    100          
131 2         11 return $_Pctile_Z_map[0]->{$dtype};
132             }
133             elsif ( $match >= $_Pctile_Z_map[-1]->{$stype} ) {
134 4         12 return $_Pctile_Z_map[-1]->{$dtype};
135             }
136             else {
137 24         25 my $i = 0;
138 24   66     4934 $i++
139             while $i < @_Pctile_Z_map
140             and $_Pctile_Z_map[$i]->{$stype} < $match;
141              
142 24 100       61 if ( $_Pctile_Z_map[$i]->{$stype} == $match ) {
143 10         21 return $_Pctile_Z_map[$i]->{$dtype};
144             }
145             else {
146 14         14 $i--;
147 14         17 my ( $lo_s, $lo_d ) = @{ $_Pctile_Z_map[$i] }{ $stype, $dtype };
  14         36  
148 14         24 my ( $hi_s, $hi_d ) =
149 14         32 @{ $_Pctile_Z_map[ $i + 1 ] }{ $stype, $dtype };
150 14         30 my $frac = ( $match - $lo_s ) / ( $hi_s - $lo_s );
151 14         45 return $lo_d + $frac * ( $hi_d - $lo_d );
152             }
153             }
154             }
155              
156             sub z_to_pct {
157 18     18 1 33 my $z = shift;
158 18 100       51 return unless defined $z;
159 17         29 my $offset = _transform_score( $z, 'Z' );
160 17 100       49 $offset *= -1 if $z < 0;
161 17         41 return 50 + $offset;
162             }
163              
164             sub pct_to_z {
165 13     13 1 5573 my $pct = shift;
166 13 50       33 return unless defined $pct;
167 13         31 my $offset = _transform_score( abs( 50 - $pct ), 'pct' );
168 13 100       41 return ( $pct < 50 ? -1 : 1 ) * $offset;
169             }
170              
171             1;
172              
173             __END__