Repository navigation
Expand file tree
/
Copy pathfloor.v
More file actions
156 lines (147 loc) · 3.37 KB
/
Copy pathfloor.v
File metadata and controls
156 lines (147 loc) · 3.37 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
module math
// floor returns the greatest integer value less than or equal to x.
//
// special cases are:
// floor(±0) = ±0
// floor(±inf) = ±inf
// floor(nan) = nan
pub fn floor(x f64) f64 {
if x == 0 || is_nan(x) || is_inf(x, 0) {
return x
}
if x < 0 {
mut d, fract := modf(-x)
if fract != 0.0 {
d = d + 1
}
return -d
}
d, _ := modf(x)
return d
}
// floorf returns the greatest integer value less than or equal to x.
//
// special cases are:
// floor(±0) = ±0
// floor(±inf) = ±inf
// floor(nan) = nan
pub fn floorf(x f32) f32 {
// TODO
return f32(floor(f64(x)))
/*
if x == 0 || is_nan(x) || is_inf(x, 0) {
return x
}
if x < 0 {
mut d, fract := modf(-x)
if fract != 0.0 {
d = d + 1
}
return -d
}
d, _ := modf(x)
return d
*/
}
// ceil returns the least integer value greater than or equal to x.
//
// special cases are:
// ceil(±0) = ±0
// ceil(±inf) = ±inf
// ceil(nan) = nan
pub fn ceil(x f64) f64 {
return -floor(-x)
}
// trunc returns the integer value of x.
//
// special cases are:
// trunc(±0) = ±0
// trunc(±inf) = ±inf
// trunc(nan) = nan
pub fn trunc(x f64) f64 {
if x == 0 || is_nan(x) || is_inf(x, 0) {
return x
}
d, _ := modf(x)
return d
}
// round returns the nearest integer, rounding half away from zero.
//
// special cases are:
// round(±0) = ±0
// round(±inf) = ±inf
// round(nan) = nan
pub fn round(x f64) f64 {
if x == 0 || is_nan(x) || is_inf(x, 0) {
return x
}
// Largest integer <= x
mut y := floor(x) // Fractional part
mut r := x - y // Round up to nearest.
if r > 0.5 {
y += 1.0
return y
}
// Round to even
if r == 0.5 {
r = y - 2.0 * floor(0.5 * y)
if r == 1.0 {
y += 1.0
}
}
// Else round down.
return y
}
// Returns the rounded float, with sig_digits of precision.
// i.e `assert round_sig(4.3239437319748394,6) == 4.323944`
pub fn round_sig(x f64, sig_digits int) f64 {
mut ret_str := '${x}'
match sig_digits {
0 { ret_str = '${x:0.0f}' }
1 { ret_str = '${x:0.1f}' }
2 { ret_str = '${x:0.2f}' }
3 { ret_str = '${x:0.3f}' }
4 { ret_str = '${x:0.4f}' }
5 { ret_str = '${x:0.5f}' }
6 { ret_str = '${x:0.6f}' }
7 { ret_str = '${x:0.7f}' }
8 { ret_str = '${x:0.8f}' }
9 { ret_str = '${x:0.9f}' }
10 { ret_str = '${x:0.10f}' }
11 { ret_str = '${x:0.11f}' }
12 { ret_str = '${x:0.12f}' }
13 { ret_str = '${x:0.13f}' }
14 { ret_str = '${x:0.14f}' }
15 { ret_str = '${x:0.15f}' }
16 { ret_str = '${x:0.16f}' }
else { ret_str = '${x}' }
}
return ret_str.f64()
}
// round_to_even returns the nearest integer, rounding ties to even.
//
// special cases are:
// round_to_even(±0) = ±0
// round_to_even(±inf) = ±inf
// round_to_even(nan) = nan
pub fn round_to_even(x f64) f64 {
mut bits := f64_bits(x)
mut e_ := (bits >> shift) & mask
if e_ >= bias {
// round abs(x) >= 1.
// - Large numbers without fractional components, infinity, and nan are unchanged.
// - Add 0.499.. or 0.5 before truncating depending on whether the truncated
// number is even or odd (respectively).
half_minus_ulp := u64(u64(1) << (shift - 1)) - 1
e_ -= u64(bias)
bits += (half_minus_ulp + (bits >> (shift - e_)) & 1) >> e_
bits &= ~(frac_mask >> e_)
} else if e_ == bias - 1 && bits & frac_mask != 0 {
// round 0.5 < abs(x) < 1.
bits = bits & sign_mask | uvone // +-1
} else {
// round abs(x) <= 0.5 including denormals.
bits &= sign_mask // +-0
}
return f64_from_bits(bits)
}