onetick-py 1.170.0__py3-none-any.whl → 1.172.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- onetick/py/__init__.py +8 -2
- onetick/py/_version.py +1 -1
- onetick/py/cache.py +3 -3
- onetick/py/callback/callbacks.py +1 -1
- onetick/py/configuration.py +35 -9
- onetick/py/core/_source/source_methods/misc.py +1 -1
- onetick/py/core/_source/source_methods/writes.py +48 -33
- onetick/py/core/column_operations/_methods/methods.py +1 -4
- onetick/py/core/column_operations/accessors/_accessor.py +4 -6
- onetick/py/core/column_operations/accessors/decimal_accessor.py +20 -8
- onetick/py/core/column_operations/accessors/dt_accessor.py +137 -68
- onetick/py/core/column_operations/accessors/float_accessor.py +35 -15
- onetick/py/core/column_operations/accessors/str_accessor.py +0 -7
- onetick/py/core/column_operations/base.py +72 -12
- onetick/py/core/multi_output_source.py +41 -2
- onetick/py/core/per_tick_script.py +2 -0
- onetick/py/db/_inspection.py +82 -49
- onetick/py/db/db.py +2 -2
- onetick/py/functions.py +7 -1
- onetick/py/math.py +374 -386
- onetick/py/misc.py +70 -38
- onetick/py/otq.py +18 -12
- onetick/py/run.py +75 -5
- onetick/py/sources/ticks.py +1 -1
- {onetick_py-1.170.0.dist-info → onetick_py-1.172.0.dist-info}/METADATA +4 -2
- {onetick_py-1.170.0.dist-info → onetick_py-1.172.0.dist-info}/RECORD +30 -30
- {onetick_py-1.170.0.dist-info → onetick_py-1.172.0.dist-info}/WHEEL +0 -0
- {onetick_py-1.170.0.dist-info → onetick_py-1.172.0.dist-info}/entry_points.txt +0 -0
- {onetick_py-1.170.0.dist-info → onetick_py-1.172.0.dist-info}/licenses/LICENSE +0 -0
- {onetick_py-1.170.0.dist-info → onetick_py-1.172.0.dist-info}/top_level.txt +0 -0
onetick/py/math.py
CHANGED
|
@@ -1,32 +1,11 @@
|
|
|
1
|
-
from typing import Optional
|
|
2
1
|
from onetick.py.core.column_operations.base import _Operation
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
class _MaxOperator(_Operation):
|
|
6
|
-
|
|
7
|
-
def __init__(self, objs):
|
|
8
|
-
from onetick.py.types import get_type_by_objects
|
|
9
|
-
|
|
10
|
-
super().__init__(dtype=get_type_by_objects(objs))
|
|
11
|
-
|
|
12
|
-
def _str_max(l_val, r_val):
|
|
13
|
-
if isinstance(r_val, list):
|
|
14
|
-
if len(r_val) > 1:
|
|
15
|
-
r_val = _str_max(r_val[0], r_val[1:])
|
|
16
|
-
else:
|
|
17
|
-
r_val = r_val[0]
|
|
18
|
-
# CASE should be uppercased because it can be used in per-tick script
|
|
19
|
-
return 'CASE({0} > {1}, 1, {0}, {1})'.format(str(l_val), str(r_val))
|
|
20
|
-
|
|
21
|
-
self._repr = _str_max(objs[0], objs[1:])
|
|
22
|
-
|
|
23
|
-
def __str__(self):
|
|
24
|
-
return self._repr
|
|
2
|
+
from onetick.py.types import value2str, nsectime, get_type_by_objects
|
|
25
3
|
|
|
26
4
|
|
|
27
5
|
def max(*objs):
|
|
28
6
|
"""
|
|
29
7
|
Returns maximum value from list of ``objs``.
|
|
8
|
+
The objects must be of the same type.
|
|
30
9
|
|
|
31
10
|
Parameters
|
|
32
11
|
----------
|
|
@@ -44,34 +23,30 @@ def max(*objs):
|
|
|
44
23
|
Time A MAX
|
|
45
24
|
0 2003-12-01 1 5
|
|
46
25
|
"""
|
|
47
|
-
|
|
26
|
+
if len(objs) < 2:
|
|
27
|
+
raise ValueError("otp.math.max expects at least 2 values to compare")
|
|
48
28
|
|
|
29
|
+
def _max_func(*objs):
|
|
30
|
+
dtype = get_type_by_objects(objs)
|
|
31
|
+
onetick_params = map(value2str, objs)
|
|
32
|
+
if dtype is nsectime:
|
|
33
|
+
onetick_params = [f'NSECTIME_TO_LONG({param})' for param in onetick_params]
|
|
34
|
+
onetick_params_str = ', '.join(onetick_params)
|
|
35
|
+
return f"NSECTIME(MAX({onetick_params_str}))", dtype
|
|
36
|
+
else:
|
|
37
|
+
onetick_params_str = ', '.join(onetick_params)
|
|
38
|
+
return f"MAX({onetick_params_str})", dtype
|
|
49
39
|
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
super().__init__(dtype=get_type_by_objects(objs))
|
|
56
|
-
|
|
57
|
-
def _str_min(l_val, r_val):
|
|
58
|
-
if isinstance(r_val, list):
|
|
59
|
-
if len(r_val) > 1:
|
|
60
|
-
r_val = _str_min(r_val[0], r_val[1:])
|
|
61
|
-
else:
|
|
62
|
-
r_val = r_val[0]
|
|
63
|
-
# CASE should be uppercased because it can be used in per-tick script
|
|
64
|
-
return 'CASE({0} < {1}, 1, {0}, {1})'.format(str(l_val), str(r_val))
|
|
65
|
-
|
|
66
|
-
self._repr = _str_min(objs[0], objs[1:])
|
|
67
|
-
|
|
68
|
-
def __str__(self):
|
|
69
|
-
return self._repr
|
|
40
|
+
return _Operation(
|
|
41
|
+
op_func=_max_func,
|
|
42
|
+
op_params=list(objs),
|
|
43
|
+
)
|
|
70
44
|
|
|
71
45
|
|
|
72
46
|
def min(*objs):
|
|
73
47
|
"""
|
|
74
48
|
Returns minimum value from list of ``objs``.
|
|
49
|
+
The objects must be of the same type.
|
|
75
50
|
|
|
76
51
|
Parameters
|
|
77
52
|
----------
|
|
@@ -89,32 +64,27 @@ def min(*objs):
|
|
|
89
64
|
Time A MIN
|
|
90
65
|
0 2003-12-01 1 -5
|
|
91
66
|
"""
|
|
92
|
-
|
|
67
|
+
if len(objs) < 2:
|
|
68
|
+
raise ValueError("otp.math.min expects at least 2 values to compare")
|
|
93
69
|
|
|
70
|
+
def _min_func(*objs):
|
|
71
|
+
dtype = get_type_by_objects(objs)
|
|
72
|
+
onetick_params = map(value2str, objs)
|
|
73
|
+
if dtype is nsectime:
|
|
74
|
+
onetick_params = [f'NSECTIME_TO_LONG({param})' for param in onetick_params]
|
|
75
|
+
onetick_params_str = ', '.join(onetick_params)
|
|
76
|
+
return f"NSECTIME(MIN({onetick_params_str}))", dtype
|
|
77
|
+
else:
|
|
78
|
+
onetick_params_str = ', '.join(onetick_params)
|
|
79
|
+
return f"MIN({onetick_params_str})", dtype
|
|
94
80
|
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
81
|
+
return _Operation(
|
|
82
|
+
op_func=_min_func,
|
|
83
|
+
op_params=list(objs),
|
|
84
|
+
)
|
|
99
85
|
|
|
100
|
-
def __init__(self, min_value: int, max_value: int, seed: Optional[int] = None):
|
|
101
|
-
super().__init__(dtype=int)
|
|
102
86
|
|
|
103
|
-
|
|
104
|
-
result = f'rand({str(min_value)}, {str(max_value)}'
|
|
105
|
-
if seed is not None:
|
|
106
|
-
result += f',{str(seed)})'
|
|
107
|
-
else:
|
|
108
|
-
result += ')'
|
|
109
|
-
return result
|
|
110
|
-
|
|
111
|
-
self._repr = _repr(min_value, max_value, seed)
|
|
112
|
-
|
|
113
|
-
def __str__(self):
|
|
114
|
-
return self._repr
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
def rand(min_value: int, max_value: int, seed: Optional[int] = None):
|
|
87
|
+
def rand(min_value, max_value, seed=None):
|
|
118
88
|
"""
|
|
119
89
|
Returns a pseudo-random value in the range between ``min_value`` and ``max_value`` (both inclusive).
|
|
120
90
|
If ``seed`` is not specified, the function produces different values each time a query is invoked.
|
|
@@ -135,6 +105,9 @@ def rand(min_value: int, max_value: int, seed: Optional[int] = None):
|
|
|
135
105
|
--------
|
|
136
106
|
>>> data = otp.Tick(A=1)
|
|
137
107
|
>>> data['RAND'] = otp.math.rand(1, 1000)
|
|
108
|
+
>>> otp.run(data) # doctest: +SKIP
|
|
109
|
+
Time A RAND
|
|
110
|
+
0 2003-12-01 1 155
|
|
138
111
|
"""
|
|
139
112
|
|
|
140
113
|
if isinstance(min_value, int) and min_value < 0:
|
|
@@ -142,29 +115,67 @@ def rand(min_value: int, max_value: int, seed: Optional[int] = None):
|
|
|
142
115
|
if isinstance(min_value, int) and isinstance(max_value, int) and min_value >= max_value:
|
|
143
116
|
raise ValueError("The `max_value` parameter should be more than `min_value`")
|
|
144
117
|
|
|
145
|
-
|
|
118
|
+
def _random_func(min_value, max_value, seed=None):
|
|
119
|
+
result = f'RAND({value2str(min_value)}, {value2str(max_value)}'
|
|
120
|
+
if seed is not None:
|
|
121
|
+
result += f', {value2str(seed)})'
|
|
122
|
+
else:
|
|
123
|
+
result += ')'
|
|
124
|
+
return result, int
|
|
146
125
|
|
|
126
|
+
return _Operation(
|
|
127
|
+
op_func=_random_func,
|
|
128
|
+
op_params=[min_value, max_value, seed],
|
|
129
|
+
)
|
|
147
130
|
|
|
148
|
-
class _Now(_Operation):
|
|
149
131
|
|
|
150
|
-
|
|
151
|
-
|
|
132
|
+
def frand(min_value=0, max_value=1, *, seed=None):
|
|
133
|
+
"""
|
|
134
|
+
Returns a pseudo-random value in the range between ``min_value`` and ``max_value``.
|
|
135
|
+
|
|
136
|
+
Parameters
|
|
137
|
+
----------
|
|
138
|
+
min_value: float, :py:class:`~onetick.py.Operation`, :py:class:`~onetick.py.Column`
|
|
139
|
+
max_value: float, :py:class:`~onetick.py.Operation`, :py:class:`~onetick.py.Column`
|
|
140
|
+
seed: int, :py:class:`~onetick.py.Operation`, :py:class:`~onetick.py.Column`
|
|
141
|
+
If not specified, the function produces different values each time a query is invoked.
|
|
142
|
+
If specified, for this seed the function produces the same sequence of values
|
|
143
|
+
each time a query is invoked.
|
|
144
|
+
|
|
145
|
+
Returns
|
|
146
|
+
-------
|
|
147
|
+
:py:class:`~onetick.py.Operation`
|
|
152
148
|
|
|
153
|
-
|
|
149
|
+
Examples
|
|
150
|
+
--------
|
|
151
|
+
>>> data = otp.Tick(A=otp.math.frand())
|
|
152
|
+
>>> otp.run(data) # doctest: +SKIP
|
|
153
|
+
Time A FRAND
|
|
154
|
+
0 2003-12-01 1 0.667519
|
|
155
|
+
"""
|
|
154
156
|
|
|
155
|
-
|
|
156
|
-
|
|
157
|
+
if isinstance(min_value, (int, float)) and min_value < 0:
|
|
158
|
+
raise ValueError("It is not possible to use negative values for the `min_value`")
|
|
159
|
+
if isinstance(min_value, (int, float)) and isinstance(max_value, (int, float)) and min_value >= max_value:
|
|
160
|
+
raise ValueError("The `max_value` parameter should be more than `min_value`")
|
|
157
161
|
|
|
158
|
-
|
|
162
|
+
def _frand_func(min_value, max_value, seed=None):
|
|
163
|
+
func_args = [min_value, max_value]
|
|
164
|
+
if seed is not None:
|
|
165
|
+
func_args.append(seed)
|
|
166
|
+
onetick_args_str = ', '.join(value2str(arg) for arg in func_args)
|
|
167
|
+
return f'FRAND({onetick_args_str})', float
|
|
159
168
|
|
|
160
|
-
|
|
161
|
-
|
|
169
|
+
return _Operation(
|
|
170
|
+
op_func=_frand_func,
|
|
171
|
+
op_params=[min_value, max_value, seed],
|
|
172
|
+
)
|
|
162
173
|
|
|
163
174
|
|
|
164
175
|
# TODO: this is not math, let's move it somewhere else
|
|
165
176
|
def now():
|
|
166
177
|
"""
|
|
167
|
-
Returns the current time expressed as the number of milliseconds since the UNIX epoch.
|
|
178
|
+
Returns the current time expressed as the number of milliseconds since the UNIX epoch in a GMT timezone.
|
|
168
179
|
|
|
169
180
|
Returns
|
|
170
181
|
-------
|
|
@@ -174,25 +185,13 @@ def now():
|
|
|
174
185
|
--------
|
|
175
186
|
>>> data = otp.Tick(A=1)
|
|
176
187
|
>>> data['NOW'] = otp.now()
|
|
188
|
+
>>> otp.run(data) # doctest: +SKIP
|
|
189
|
+
Time A NOW
|
|
190
|
+
0 2003-12-01 1 2025-09-29 09:09:00.158
|
|
177
191
|
"""
|
|
178
|
-
return
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
class _Ln(_Operation):
|
|
182
|
-
"""
|
|
183
|
-
Compute the natural logarithm.
|
|
184
|
-
"""
|
|
185
|
-
|
|
186
|
-
def __init__(self, value):
|
|
187
|
-
super().__init__(dtype=float)
|
|
188
|
-
|
|
189
|
-
def _repr(value):
|
|
190
|
-
return f'LOG({str(value)})'
|
|
191
|
-
|
|
192
|
-
self._repr = _repr(value)
|
|
193
|
-
|
|
194
|
-
def __str__(self):
|
|
195
|
-
return self._repr
|
|
192
|
+
return _Operation(
|
|
193
|
+
op_func=lambda: ('NOW()', nsectime),
|
|
194
|
+
)
|
|
196
195
|
|
|
197
196
|
|
|
198
197
|
def ln(value):
|
|
@@ -217,26 +216,15 @@ def ln(value):
|
|
|
217
216
|
|
|
218
217
|
See Also
|
|
219
218
|
--------
|
|
220
|
-
onetick.py.math.exp
|
|
219
|
+
:py:func:`onetick.py.math.exp`
|
|
221
220
|
"""
|
|
222
|
-
return
|
|
221
|
+
return _Operation(
|
|
222
|
+
op_func=lambda v: (f'LOG({value2str(v)})', float),
|
|
223
|
+
op_params=[value],
|
|
224
|
+
)
|
|
223
225
|
|
|
224
226
|
|
|
225
|
-
|
|
226
|
-
"""
|
|
227
|
-
Compute the base-10 logarithm.
|
|
228
|
-
"""
|
|
229
|
-
|
|
230
|
-
def __init__(self, value):
|
|
231
|
-
super().__init__(dtype=float)
|
|
232
|
-
|
|
233
|
-
def _repr(value):
|
|
234
|
-
return f'LOG10({str(value)})'
|
|
235
|
-
|
|
236
|
-
self._repr = _repr(value)
|
|
237
|
-
|
|
238
|
-
def __str__(self):
|
|
239
|
-
return self._repr
|
|
227
|
+
log = ln
|
|
240
228
|
|
|
241
229
|
|
|
242
230
|
def log10(value):
|
|
@@ -259,24 +247,10 @@ def log10(value):
|
|
|
259
247
|
Time A LOG10
|
|
260
248
|
0 2003-12-01 1 2.0
|
|
261
249
|
"""
|
|
262
|
-
return
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
"""
|
|
267
|
-
Compute the natural exponent.
|
|
268
|
-
"""
|
|
269
|
-
|
|
270
|
-
def __init__(self, value):
|
|
271
|
-
super().__init__(dtype=float)
|
|
272
|
-
|
|
273
|
-
def _repr(value):
|
|
274
|
-
return f'EXP({str(value)})'
|
|
275
|
-
|
|
276
|
-
self._repr = _repr(value)
|
|
277
|
-
|
|
278
|
-
def __str__(self):
|
|
279
|
-
return self._repr
|
|
250
|
+
return _Operation(
|
|
251
|
+
op_func=lambda v: (f'LOG10({value2str(v)})', float),
|
|
252
|
+
op_params=[value],
|
|
253
|
+
)
|
|
280
254
|
|
|
281
255
|
|
|
282
256
|
def exp(value):
|
|
@@ -301,26 +275,12 @@ def exp(value):
|
|
|
301
275
|
|
|
302
276
|
See Also
|
|
303
277
|
--------
|
|
304
|
-
onetick.py.math.ln
|
|
278
|
+
:py:func:`onetick.py.math.ln`
|
|
305
279
|
"""
|
|
306
|
-
return
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
"""
|
|
311
|
-
Compute the square root.
|
|
312
|
-
"""
|
|
313
|
-
|
|
314
|
-
def __init__(self, value):
|
|
315
|
-
super().__init__(dtype=float)
|
|
316
|
-
|
|
317
|
-
def _repr(value):
|
|
318
|
-
return f'SQRT({str(value)})'
|
|
319
|
-
|
|
320
|
-
self._repr = _repr(value)
|
|
321
|
-
|
|
322
|
-
def __str__(self):
|
|
323
|
-
return self._repr
|
|
280
|
+
return _Operation(
|
|
281
|
+
op_func=lambda v: (f'EXP({value2str(v)})', float),
|
|
282
|
+
op_params=[value],
|
|
283
|
+
)
|
|
324
284
|
|
|
325
285
|
|
|
326
286
|
def sqrt(value):
|
|
@@ -343,24 +303,10 @@ def sqrt(value):
|
|
|
343
303
|
Time A SQRT
|
|
344
304
|
0 2003-12-01 1 2.0
|
|
345
305
|
"""
|
|
346
|
-
return
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
"""
|
|
351
|
-
Get the sign of value.
|
|
352
|
-
"""
|
|
353
|
-
|
|
354
|
-
def __init__(self, value):
|
|
355
|
-
super().__init__(dtype=int)
|
|
356
|
-
|
|
357
|
-
def _repr(value):
|
|
358
|
-
return f'SIGN({str(value)})'
|
|
359
|
-
|
|
360
|
-
self._repr = _repr(value)
|
|
361
|
-
|
|
362
|
-
def __str__(self):
|
|
363
|
-
return self._repr
|
|
306
|
+
return _Operation(
|
|
307
|
+
op_func=lambda v: (f'SQRT({value2str(v)})', float),
|
|
308
|
+
op_params=[value],
|
|
309
|
+
)
|
|
364
310
|
|
|
365
311
|
|
|
366
312
|
def sign(value):
|
|
@@ -385,24 +331,10 @@ def sign(value):
|
|
|
385
331
|
Time A SIGN_POS SIGN_ZERO SIGN_NEG
|
|
386
332
|
0 2003-12-01 1 1 0 -1
|
|
387
333
|
"""
|
|
388
|
-
return
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
"""
|
|
393
|
-
Compute the ``base`` to the power of the ``exponent``.
|
|
394
|
-
"""
|
|
395
|
-
|
|
396
|
-
def __init__(self, base, exponent):
|
|
397
|
-
super().__init__(dtype=float)
|
|
398
|
-
|
|
399
|
-
def _repr(base, exponent):
|
|
400
|
-
return f'POWER({str(base)}, {str(exponent)})'
|
|
401
|
-
|
|
402
|
-
self._repr = _repr(base, exponent)
|
|
403
|
-
|
|
404
|
-
def __str__(self):
|
|
405
|
-
return self._repr
|
|
334
|
+
return _Operation(
|
|
335
|
+
op_func=lambda v: (f'SIGN({value2str(v)})', int),
|
|
336
|
+
op_params=[value],
|
|
337
|
+
)
|
|
406
338
|
|
|
407
339
|
|
|
408
340
|
def pow(base, exponent):
|
|
@@ -426,21 +358,10 @@ def pow(base, exponent):
|
|
|
426
358
|
Time A RES
|
|
427
359
|
0 2003-12-01 2 1024.0
|
|
428
360
|
"""
|
|
429
|
-
return
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
def __init__(self):
|
|
435
|
-
super().__init__(dtype=float)
|
|
436
|
-
|
|
437
|
-
def _repr():
|
|
438
|
-
return 'PI()'
|
|
439
|
-
|
|
440
|
-
self._repr = _repr()
|
|
441
|
-
|
|
442
|
-
def __str__(self):
|
|
443
|
-
return self._repr
|
|
361
|
+
return _Operation(
|
|
362
|
+
op_func=lambda b, e: (f'POWER({value2str(b)}, {value2str(e)})', float),
|
|
363
|
+
op_params=[base, exponent],
|
|
364
|
+
)
|
|
444
365
|
|
|
445
366
|
|
|
446
367
|
def pi():
|
|
@@ -459,24 +380,9 @@ def pi():
|
|
|
459
380
|
Time A PI
|
|
460
381
|
0 2003-12-01 1 3.141593
|
|
461
382
|
"""
|
|
462
|
-
return
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
class _Sin(_Operation):
|
|
466
|
-
"""
|
|
467
|
-
Returns the value of trigonometric function `sin` for the given angle number expressed in radians.
|
|
468
|
-
"""
|
|
469
|
-
|
|
470
|
-
def __init__(self, value):
|
|
471
|
-
super().__init__(dtype=float)
|
|
472
|
-
|
|
473
|
-
def _repr(value):
|
|
474
|
-
return f'SIN({str(value)})'
|
|
475
|
-
|
|
476
|
-
self._repr = _repr(value)
|
|
477
|
-
|
|
478
|
-
def __str__(self):
|
|
479
|
-
return self._repr
|
|
383
|
+
return _Operation(
|
|
384
|
+
op_func=lambda: ('PI()', float),
|
|
385
|
+
)
|
|
480
386
|
|
|
481
387
|
|
|
482
388
|
def sin(value):
|
|
@@ -501,27 +407,13 @@ def sin(value):
|
|
|
501
407
|
|
|
502
408
|
See Also
|
|
503
409
|
--------
|
|
504
|
-
:py:
|
|
410
|
+
:py:func:`onetick.py.math.pi`
|
|
505
411
|
:py:func:`onetick.py.math.asin`
|
|
506
412
|
"""
|
|
507
|
-
return
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
"""
|
|
512
|
-
Returns the value of trigonometric function `cos` for the given angle number expressed in radians.
|
|
513
|
-
"""
|
|
514
|
-
|
|
515
|
-
def __init__(self, value):
|
|
516
|
-
super().__init__(dtype=float)
|
|
517
|
-
|
|
518
|
-
def _repr(value):
|
|
519
|
-
return f'COS({str(value)})'
|
|
520
|
-
|
|
521
|
-
self._repr = _repr(value)
|
|
522
|
-
|
|
523
|
-
def __str__(self):
|
|
524
|
-
return self._repr
|
|
413
|
+
return _Operation(
|
|
414
|
+
op_func=lambda v: (f'SIN({value2str(v)})', float),
|
|
415
|
+
op_params=[value],
|
|
416
|
+
)
|
|
525
417
|
|
|
526
418
|
|
|
527
419
|
def cos(value):
|
|
@@ -546,27 +438,13 @@ def cos(value):
|
|
|
546
438
|
|
|
547
439
|
See Also
|
|
548
440
|
--------
|
|
549
|
-
:py:
|
|
441
|
+
:py:func:`onetick.py.math.pi`
|
|
550
442
|
:py:func:`onetick.py.math.acos`
|
|
551
443
|
"""
|
|
552
|
-
return
|
|
553
|
-
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
"""
|
|
557
|
-
Returns the value of trigonometric function `tan` for the given angle number expressed in radians.
|
|
558
|
-
"""
|
|
559
|
-
|
|
560
|
-
def __init__(self, value):
|
|
561
|
-
super().__init__(dtype=float)
|
|
562
|
-
|
|
563
|
-
def _repr(value):
|
|
564
|
-
return f'TAN({str(value)})'
|
|
565
|
-
|
|
566
|
-
self._repr = _repr(value)
|
|
567
|
-
|
|
568
|
-
def __str__(self):
|
|
569
|
-
return self._repr
|
|
444
|
+
return _Operation(
|
|
445
|
+
op_func=lambda v: (f'COS({value2str(v)})', float),
|
|
446
|
+
op_params=[value],
|
|
447
|
+
)
|
|
570
448
|
|
|
571
449
|
|
|
572
450
|
def tan(value):
|
|
@@ -591,27 +469,13 @@ def tan(value):
|
|
|
591
469
|
|
|
592
470
|
See Also
|
|
593
471
|
--------
|
|
594
|
-
:py:
|
|
472
|
+
:py:func:`onetick.py.math.pi`
|
|
595
473
|
:py:func:`onetick.py.math.atan`
|
|
596
474
|
"""
|
|
597
|
-
return
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
|
|
601
|
-
"""
|
|
602
|
-
Returns the value of trigonometric function `cot` for the given angle number expressed in radians.
|
|
603
|
-
"""
|
|
604
|
-
|
|
605
|
-
def __init__(self, value):
|
|
606
|
-
super().__init__(dtype=float)
|
|
607
|
-
|
|
608
|
-
def _repr(value):
|
|
609
|
-
return f'COT({str(value)})'
|
|
610
|
-
|
|
611
|
-
self._repr = _repr(value)
|
|
612
|
-
|
|
613
|
-
def __str__(self):
|
|
614
|
-
return self._repr
|
|
475
|
+
return _Operation(
|
|
476
|
+
op_func=lambda v: (f'TAN({value2str(v)})', float),
|
|
477
|
+
op_params=[value],
|
|
478
|
+
)
|
|
615
479
|
|
|
616
480
|
|
|
617
481
|
def cot(value):
|
|
@@ -636,27 +500,13 @@ def cot(value):
|
|
|
636
500
|
|
|
637
501
|
See Also
|
|
638
502
|
--------
|
|
639
|
-
:py:
|
|
503
|
+
:py:func:`onetick.py.math.pi`
|
|
640
504
|
:py:func:`onetick.py.math.acot`
|
|
641
505
|
"""
|
|
642
|
-
return
|
|
643
|
-
|
|
644
|
-
|
|
645
|
-
|
|
646
|
-
"""
|
|
647
|
-
Returns the value of inverse trigonometric function `arcsin`.
|
|
648
|
-
"""
|
|
649
|
-
|
|
650
|
-
def __init__(self, value):
|
|
651
|
-
super().__init__(dtype=float)
|
|
652
|
-
|
|
653
|
-
def _repr(value):
|
|
654
|
-
return f'ASIN({str(value)})'
|
|
655
|
-
|
|
656
|
-
self._repr = _repr(value)
|
|
657
|
-
|
|
658
|
-
def __str__(self):
|
|
659
|
-
return self._repr
|
|
506
|
+
return _Operation(
|
|
507
|
+
op_func=lambda v: (f'COT({value2str(v)})', float),
|
|
508
|
+
op_params=[value],
|
|
509
|
+
)
|
|
660
510
|
|
|
661
511
|
|
|
662
512
|
def asin(value):
|
|
@@ -689,32 +539,18 @@ def asin(value):
|
|
|
689
539
|
|
|
690
540
|
See Also
|
|
691
541
|
--------
|
|
692
|
-
:py:
|
|
542
|
+
:py:func:`onetick.py.math.pi`
|
|
693
543
|
:py:func:`onetick.py.math.sin`
|
|
694
544
|
"""
|
|
695
|
-
return
|
|
545
|
+
return _Operation(
|
|
546
|
+
op_func=lambda v: (f'ASIN({value2str(v)})', float),
|
|
547
|
+
op_params=[value],
|
|
548
|
+
)
|
|
696
549
|
|
|
697
550
|
|
|
698
551
|
arcsin = asin
|
|
699
552
|
|
|
700
553
|
|
|
701
|
-
class _Acos(_Operation):
|
|
702
|
-
"""
|
|
703
|
-
Returns the value of inverse trigonometric function `arccos`.
|
|
704
|
-
"""
|
|
705
|
-
|
|
706
|
-
def __init__(self, value):
|
|
707
|
-
super().__init__(dtype=float)
|
|
708
|
-
|
|
709
|
-
def _repr(value):
|
|
710
|
-
return f'ACOS({str(value)})'
|
|
711
|
-
|
|
712
|
-
self._repr = _repr(value)
|
|
713
|
-
|
|
714
|
-
def __str__(self):
|
|
715
|
-
return self._repr
|
|
716
|
-
|
|
717
|
-
|
|
718
554
|
def acos(value):
|
|
719
555
|
"""
|
|
720
556
|
Returns the value of inverse trigonometric function `arccos`.
|
|
@@ -745,32 +581,18 @@ def acos(value):
|
|
|
745
581
|
|
|
746
582
|
See Also
|
|
747
583
|
--------
|
|
748
|
-
:py:
|
|
584
|
+
:py:func:`onetick.py.math.pi`
|
|
749
585
|
:py:func:`onetick.py.math.cos`
|
|
750
586
|
"""
|
|
751
|
-
return
|
|
587
|
+
return _Operation(
|
|
588
|
+
op_func=lambda v: (f'ACOS({value2str(v)})', float),
|
|
589
|
+
op_params=[value],
|
|
590
|
+
)
|
|
752
591
|
|
|
753
592
|
|
|
754
593
|
arccos = acos
|
|
755
594
|
|
|
756
595
|
|
|
757
|
-
class _Atan(_Operation):
|
|
758
|
-
"""
|
|
759
|
-
Returns the value of inverse trigonometric function `arctan`.
|
|
760
|
-
"""
|
|
761
|
-
|
|
762
|
-
def __init__(self, value):
|
|
763
|
-
super().__init__(dtype=float)
|
|
764
|
-
|
|
765
|
-
def _repr(value):
|
|
766
|
-
return f'ATAN({str(value)})'
|
|
767
|
-
|
|
768
|
-
self._repr = _repr(value)
|
|
769
|
-
|
|
770
|
-
def __str__(self):
|
|
771
|
-
return self._repr
|
|
772
|
-
|
|
773
|
-
|
|
774
596
|
def atan(value):
|
|
775
597
|
"""
|
|
776
598
|
Returns the value of inverse trigonometric function `arctan`.
|
|
@@ -801,32 +623,18 @@ def atan(value):
|
|
|
801
623
|
|
|
802
624
|
See Also
|
|
803
625
|
--------
|
|
804
|
-
:py:
|
|
626
|
+
:py:func:`onetick.py.math.pi`
|
|
805
627
|
:py:func:`onetick.py.math.tan`
|
|
806
628
|
"""
|
|
807
|
-
return
|
|
629
|
+
return _Operation(
|
|
630
|
+
op_func=lambda v: (f'ATAN({value2str(v)})', float),
|
|
631
|
+
op_params=[value],
|
|
632
|
+
)
|
|
808
633
|
|
|
809
634
|
|
|
810
635
|
arctan = atan
|
|
811
636
|
|
|
812
637
|
|
|
813
|
-
class _Acot(_Operation):
|
|
814
|
-
"""
|
|
815
|
-
Returns the value of inverse trigonometric function `arccot`.
|
|
816
|
-
"""
|
|
817
|
-
|
|
818
|
-
def __init__(self, value):
|
|
819
|
-
super().__init__(dtype=float)
|
|
820
|
-
|
|
821
|
-
def _repr(value):
|
|
822
|
-
return f'ACOT({str(value)})'
|
|
823
|
-
|
|
824
|
-
self._repr = _repr(value)
|
|
825
|
-
|
|
826
|
-
def __str__(self):
|
|
827
|
-
return self._repr
|
|
828
|
-
|
|
829
|
-
|
|
830
638
|
def acot(value):
|
|
831
639
|
"""
|
|
832
640
|
Returns the value of inverse trigonometric function `arccot`.
|
|
@@ -857,35 +665,21 @@ def acot(value):
|
|
|
857
665
|
|
|
858
666
|
See Also
|
|
859
667
|
--------
|
|
860
|
-
:py:
|
|
668
|
+
:py:func:`onetick.py.math.pi`
|
|
861
669
|
:py:func:`onetick.py.math.cot`
|
|
862
670
|
"""
|
|
863
|
-
return
|
|
671
|
+
return _Operation(
|
|
672
|
+
op_func=lambda v: (f'ACOT({value2str(v)})', float),
|
|
673
|
+
op_params=[value],
|
|
674
|
+
)
|
|
864
675
|
|
|
865
676
|
|
|
866
677
|
arccot = acot
|
|
867
678
|
|
|
868
679
|
|
|
869
|
-
class _Mod(_Operation):
|
|
870
|
-
"""
|
|
871
|
-
Implements the remainder from dividing ``value1`` by ``value2``
|
|
872
|
-
"""
|
|
873
|
-
|
|
874
|
-
def __init__(self, value1, value2):
|
|
875
|
-
super().__init__(dtype=int)
|
|
876
|
-
|
|
877
|
-
def _repr(value1, value2):
|
|
878
|
-
return f'MOD({str(value1)}, {str(value2)})'
|
|
879
|
-
|
|
880
|
-
self._repr = _repr(value1, value2)
|
|
881
|
-
|
|
882
|
-
def __str__(self):
|
|
883
|
-
return self._repr
|
|
884
|
-
|
|
885
|
-
|
|
886
680
|
def mod(value1, value2):
|
|
887
681
|
"""
|
|
888
|
-
Computes the remainder from dividing ``value1`` by ``value2
|
|
682
|
+
Computes the remainder from dividing ``value1`` by ``value2``.
|
|
889
683
|
|
|
890
684
|
Parameters
|
|
891
685
|
----------
|
|
@@ -904,29 +698,74 @@ def mod(value1, value2):
|
|
|
904
698
|
Time A MOD
|
|
905
699
|
0 2003-12-01 100 28
|
|
906
700
|
"""
|
|
907
|
-
return
|
|
701
|
+
return _Operation(
|
|
702
|
+
op_func=lambda v1, v2: (f'MOD({value2str(v1)}, {value2str(v2)})', int),
|
|
703
|
+
op_params=[value1, value2],
|
|
704
|
+
)
|
|
908
705
|
|
|
909
706
|
|
|
910
|
-
|
|
707
|
+
def div(value1, value2):
|
|
911
708
|
"""
|
|
912
|
-
|
|
709
|
+
Computes the quotient by dividing ``value1`` by ``value2``.
|
|
710
|
+
|
|
711
|
+
Parameters
|
|
712
|
+
----------
|
|
713
|
+
value1: int, float, :py:class:`~onetick.py.Operation`, :py:class:`~onetick.py.Column`
|
|
714
|
+
value2: int, float, :py:class:`~onetick.py.Operation`, :py:class:`~onetick.py.Column`
|
|
715
|
+
|
|
716
|
+
Returns
|
|
717
|
+
-------
|
|
718
|
+
:py:class:`~onetick.py.Operation`
|
|
719
|
+
|
|
720
|
+
Examples
|
|
721
|
+
--------
|
|
722
|
+
>>> data = otp.Tick(A=100)
|
|
723
|
+
>>> data['DIV'] = otp.math.div(data['A'], 72)
|
|
724
|
+
>>> otp.run(data)
|
|
725
|
+
Time A DIV
|
|
726
|
+
0 2003-12-01 100 1
|
|
913
727
|
"""
|
|
728
|
+
return _Operation(
|
|
729
|
+
op_func=lambda v1, v2: (f'DIV({value2str(v1)}, {value2str(v2)})', int),
|
|
730
|
+
op_params=[value1, value2],
|
|
731
|
+
)
|
|
914
732
|
|
|
915
|
-
def __init__(self, value):
|
|
916
|
-
super().__init__(dtype=int)
|
|
917
733
|
|
|
918
|
-
|
|
919
|
-
|
|
734
|
+
def gcd(value1, value2):
|
|
735
|
+
"""
|
|
736
|
+
Computes the greatest common divisor between ``value1`` and ``value2``.
|
|
920
737
|
|
|
921
|
-
|
|
738
|
+
Parameters
|
|
739
|
+
----------
|
|
740
|
+
value1: int, float, :py:class:`~onetick.py.Operation`, :py:class:`~onetick.py.Column`
|
|
741
|
+
value2: int, float, :py:class:`~onetick.py.Operation`, :py:class:`~onetick.py.Column`
|
|
922
742
|
|
|
923
|
-
|
|
924
|
-
|
|
743
|
+
Returns
|
|
744
|
+
-------
|
|
745
|
+
:py:class:`~onetick.py.Operation`
|
|
746
|
+
|
|
747
|
+
Examples
|
|
748
|
+
--------
|
|
749
|
+
>>> data = otp.Tick(A=99)
|
|
750
|
+
>>> data['GCD'] = otp.math.gcd(data['A'], 72)
|
|
751
|
+
>>> otp.run(data)
|
|
752
|
+
Time A GCD
|
|
753
|
+
0 2003-12-01 99 9
|
|
754
|
+
"""
|
|
755
|
+
return _Operation(
|
|
756
|
+
op_func=lambda v1, v2: (f'GCD({value2str(v1)}, {value2str(v2)})', int),
|
|
757
|
+
op_params=[value1, value2],
|
|
758
|
+
)
|
|
925
759
|
|
|
926
760
|
|
|
927
761
|
def floor(value):
|
|
928
762
|
"""
|
|
929
|
-
Returns a
|
|
763
|
+
Returns a float value representing the largest number that is less than or equal to the ``value``.
|
|
764
|
+
|
|
765
|
+
Note
|
|
766
|
+
----
|
|
767
|
+
Rounding :class:`otp.nan <onetick.py.nan>` returns NaN
|
|
768
|
+
and rounding :class:`otp.inf <onetick.py.inf>` returns Infinity.
|
|
930
769
|
|
|
931
770
|
Parameters
|
|
932
771
|
----------
|
|
@@ -938,10 +777,159 @@ def floor(value):
|
|
|
938
777
|
|
|
939
778
|
Examples
|
|
940
779
|
--------
|
|
941
|
-
>>> data = otp.
|
|
780
|
+
>>> data = otp.Ticks(A=[-1.7, -1.5, -1.2, -1, 0 , 1, 1.2, 1.5, 1.7, -otp.inf, otp.inf, otp.nan])
|
|
942
781
|
>>> data['FLOOR'] = otp.math.floor(data['A'])
|
|
943
782
|
>>> otp.run(data)
|
|
944
|
-
|
|
945
|
-
0
|
|
783
|
+
Time A FLOOR
|
|
784
|
+
0 2003-12-01 00:00:00.000 -1.7 -2.0
|
|
785
|
+
1 2003-12-01 00:00:00.001 -1.5 -2.0
|
|
786
|
+
2 2003-12-01 00:00:00.002 -1.2 -2.0
|
|
787
|
+
3 2003-12-01 00:00:00.003 -1.0 -1.0
|
|
788
|
+
4 2003-12-01 00:00:00.004 0.0 0.0
|
|
789
|
+
5 2003-12-01 00:00:00.005 1.0 1.0
|
|
790
|
+
6 2003-12-01 00:00:00.006 1.2 1.0
|
|
791
|
+
7 2003-12-01 00:00:00.007 1.5 1.0
|
|
792
|
+
8 2003-12-01 00:00:00.008 1.7 1.0
|
|
793
|
+
9 2003-12-01 00:00:00.009 -inf -inf
|
|
794
|
+
10 2003-12-01 00:00:00.010 inf inf
|
|
795
|
+
11 2003-12-01 00:00:00.011 NaN NaN
|
|
796
|
+
"""
|
|
797
|
+
def fun(v):
|
|
798
|
+
v = value2str(v)
|
|
799
|
+
return f'CASE({v}, NAN(), NAN(), INFINITY(), INFINITY(), -INFINITY(), -INFINITY(), FLOOR({v}) * 1.0)', float
|
|
800
|
+
|
|
801
|
+
return _Operation(
|
|
802
|
+
op_func=fun,
|
|
803
|
+
op_params=[value],
|
|
804
|
+
)
|
|
805
|
+
|
|
806
|
+
|
|
807
|
+
def ceil(value):
|
|
808
|
+
"""
|
|
809
|
+
Returns a float value representing the smallest number that is greater than or equal to the ``value``.
|
|
810
|
+
|
|
811
|
+
Note
|
|
812
|
+
----
|
|
813
|
+
Rounding :class:`otp.nan <onetick.py.nan>` returns NaN
|
|
814
|
+
and rounding :class:`otp.inf <onetick.py.inf>` returns Infinity.
|
|
815
|
+
|
|
816
|
+
Parameters
|
|
817
|
+
----------
|
|
818
|
+
value: int, float, :py:class:`~onetick.py.Operation`, :py:class:`~onetick.py.Column`
|
|
819
|
+
|
|
820
|
+
Returns
|
|
821
|
+
-------
|
|
822
|
+
:py:class:`~onetick.py.Operation`
|
|
823
|
+
|
|
824
|
+
Examples
|
|
825
|
+
--------
|
|
826
|
+
>>> data = otp.Ticks(A=[-1.7, -1.5, -1.2, -1, 0 , 1, 1.2, 1.5, 1.7, -otp.inf, otp.inf, otp.nan])
|
|
827
|
+
>>> data['CEIL'] = otp.math.ceil(data['A'])
|
|
828
|
+
>>> otp.run(data)
|
|
829
|
+
Time A CEIL
|
|
830
|
+
0 2003-12-01 00:00:00.000 -1.7 -1.0
|
|
831
|
+
1 2003-12-01 00:00:00.001 -1.5 -1.0
|
|
832
|
+
2 2003-12-01 00:00:00.002 -1.2 -1.0
|
|
833
|
+
3 2003-12-01 00:00:00.003 -1.0 -1.0
|
|
834
|
+
4 2003-12-01 00:00:00.004 0.0 0.0
|
|
835
|
+
5 2003-12-01 00:00:00.005 1.0 1.0
|
|
836
|
+
6 2003-12-01 00:00:00.006 1.2 2.0
|
|
837
|
+
7 2003-12-01 00:00:00.007 1.5 2.0
|
|
838
|
+
8 2003-12-01 00:00:00.008 1.7 2.0
|
|
839
|
+
9 2003-12-01 00:00:00.009 -inf -inf
|
|
840
|
+
10 2003-12-01 00:00:00.010 inf inf
|
|
841
|
+
11 2003-12-01 00:00:00.011 NaN NaN
|
|
946
842
|
"""
|
|
947
|
-
|
|
843
|
+
def fun(v):
|
|
844
|
+
v = value2str(v)
|
|
845
|
+
return f'CASE({v}, NAN(), NAN(), INFINITY(), INFINITY(), -INFINITY(), -INFINITY(), CEIL({v}) * 1.0)', float
|
|
846
|
+
|
|
847
|
+
return _Operation(
|
|
848
|
+
op_func=fun,
|
|
849
|
+
op_params=[value],
|
|
850
|
+
)
|
|
851
|
+
|
|
852
|
+
|
|
853
|
+
def round(value, precision=0, rounding_method='upward'):
|
|
854
|
+
"""
|
|
855
|
+
Rounds value with specified ``precision`` and ``rounding_method``.
|
|
856
|
+
|
|
857
|
+
Rounding :class:`otp.nan <onetick.py.nan>` returns NaN
|
|
858
|
+
and rounding :class:`otp.inf <onetick.py.inf>` returns Infinity.
|
|
859
|
+
|
|
860
|
+
Parameters
|
|
861
|
+
----------
|
|
862
|
+
precision: int
|
|
863
|
+
Number from -12 to 12.
|
|
864
|
+
Positive precision is precision after the floating point.
|
|
865
|
+
Negative precision is precision before the floating point (and the fraction part is dropped in this case).
|
|
866
|
+
rounding_method: str
|
|
867
|
+
Used for values that are exactly half-way between two integers (when the fraction part of value is exactly 0.5).
|
|
868
|
+
Available values are **upward**, **downward**, **towards_zero**, **away_from_zero**.
|
|
869
|
+
Default is **upward**.
|
|
870
|
+
|
|
871
|
+
Examples
|
|
872
|
+
--------
|
|
873
|
+
|
|
874
|
+
Different rounding methods produce different results for values that are exactly half-way between two integers:
|
|
875
|
+
|
|
876
|
+
>>> t = otp.Ticks(A=[-123.45, 123.45, -123.4, 123.6])
|
|
877
|
+
>>> t['UPWARD'] = otp.math.round(t['A'], precision=1, rounding_method='upward')
|
|
878
|
+
>>> t['DOWNWARD'] = otp.math.round(t['A'], precision=1, rounding_method='downward')
|
|
879
|
+
>>> t['TOWARDS_ZERO'] = otp.math.round(t['A'], precision=1, rounding_method='towards_zero')
|
|
880
|
+
>>> t['AWAY_FROM_ZERO'] = otp.math.round(t['A'], precision=1, rounding_method='away_from_zero')
|
|
881
|
+
>>> otp.run(t).head(2)
|
|
882
|
+
Time A UPWARD DOWNWARD TOWARDS_ZERO AWAY_FROM_ZERO
|
|
883
|
+
0 2003-12-01 00:00:00.000 -123.45 -123.4 -123.5 -123.4 -123.5
|
|
884
|
+
1 2003-12-01 00:00:00.001 123.45 123.5 123.4 123.4 123.5
|
|
885
|
+
|
|
886
|
+
Note that for other cases all methods produce the same results:
|
|
887
|
+
|
|
888
|
+
>>> otp.run(t).tail(2)
|
|
889
|
+
Time A UPWARD DOWNWARD TOWARDS_ZERO AWAY_FROM_ZERO
|
|
890
|
+
2 2003-12-01 00:00:00.002 -123.4 -123.4 -123.4 -123.4 -123.4
|
|
891
|
+
3 2003-12-01 00:00:00.003 123.6 123.6 123.6 123.6 123.6
|
|
892
|
+
|
|
893
|
+
Positive precision truncates to the number of digits *after* floating point:
|
|
894
|
+
|
|
895
|
+
>>> t = otp.Ticks(A=[-123.45, 123.45])
|
|
896
|
+
>>> t['ROUND1'] = otp.math.round(t['A'], 1)
|
|
897
|
+
>>> t['ROUND2'] = otp.math.round(t['A'], 2)
|
|
898
|
+
>>> otp.run(t)
|
|
899
|
+
Time A ROUND1 ROUND2
|
|
900
|
+
0 2003-12-01 00:00:00.000 -123.45 -123.4 -123.45
|
|
901
|
+
1 2003-12-01 00:00:00.001 123.45 123.5 123.45
|
|
902
|
+
|
|
903
|
+
Negative precision truncates to the number of digits *before* floating point
|
|
904
|
+
(and the fraction part is dropped in this case):
|
|
905
|
+
|
|
906
|
+
>>> t = otp.Ticks(A=[-123.45, 123.45])
|
|
907
|
+
>>> t['ROUND_M1'] = otp.math.round(t['A'], -1)
|
|
908
|
+
>>> t['ROUND_M2'] = otp.math.round(t['A'], -2)
|
|
909
|
+
>>> otp.run(t)
|
|
910
|
+
Time A ROUND_M1 ROUND_M2
|
|
911
|
+
0 2003-12-01 00:00:00.000 -123.45 -120.0 -100.0
|
|
912
|
+
1 2003-12-01 00:00:00.001 123.45 120.0 100.0
|
|
913
|
+
|
|
914
|
+
Rounding :class:`otp.nan <onetick.py.nan>` returns NaN
|
|
915
|
+
and rounding :class:`otp.inf <onetick.py.inf>` returns Infinity in all cases:
|
|
916
|
+
|
|
917
|
+
>>> t = otp.Ticks(A=[otp.inf, -otp.inf, otp.nan])
|
|
918
|
+
>>> t['ROUND_0'] = otp.math.round(t['A'])
|
|
919
|
+
>>> t['ROUND_P2'] = otp.math.round(t['A'], 2)
|
|
920
|
+
>>> t['ROUND_M2'] = otp.math.round(t['A'], -2)
|
|
921
|
+
>>> otp.run(t)
|
|
922
|
+
Time A ROUND_0 ROUND_P2 ROUND_M2
|
|
923
|
+
0 2003-12-01 00:00:00.000 inf inf inf inf
|
|
924
|
+
1 2003-12-01 00:00:00.001 -inf -inf -inf -inf
|
|
925
|
+
2 2003-12-01 00:00:00.002 NaN NaN NaN NaN
|
|
926
|
+
"""
|
|
927
|
+
if not -12 <= precision <= 12:
|
|
928
|
+
raise ValueError("Parameter 'precision' must be an integer in range [-12, 12]")
|
|
929
|
+
supported_rounding_methods = {'upward', 'downward', 'towards_zero', 'away_from_zero'}
|
|
930
|
+
if rounding_method not in supported_rounding_methods:
|
|
931
|
+
raise ValueError(f"Parameter 'rounding_method' must be one of {supported_rounding_methods}")
|
|
932
|
+
return _Operation(
|
|
933
|
+
op_func=lambda v, p, r: (f'ROUND_DOUBLE({value2str(v)},{value2str(p)},{value2str(r)})', float),
|
|
934
|
+
op_params=[value, precision, rounding_method],
|
|
935
|
+
)
|