polars-ta 0.4.5__py3-none-any.whl → 0.4.6__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.
- polars_ta/_version.py +1 -1
- polars_ta/prefix/tdx.py +55 -0
- polars_ta/tdx/__init__.py +2 -0
- polars_ta/tdx/pattern_feature.py +236 -0
- polars_ta/tdx/reference.py +6 -0
- polars_ta/tdx/trend_feature.py +449 -0
- polars_ta/wq/arithmetic.py +450 -20
- polars_ta/wq/cross_sectional.py +10 -0
- polars_ta/wq/time_series.py +36 -3
- {polars_ta-0.4.5.dist-info → polars_ta-0.4.6.dist-info}/METADATA +2 -2
- {polars_ta-0.4.5.dist-info → polars_ta-0.4.6.dist-info}/RECORD +14 -12
- {polars_ta-0.4.5.dist-info → polars_ta-0.4.6.dist-info}/WHEEL +1 -1
- {polars_ta-0.4.5.dist-info → polars_ta-0.4.6.dist-info}/LICENSE +0 -0
- {polars_ta-0.4.5.dist-info → polars_ta-0.4.6.dist-info}/top_level.txt +0 -0
polars_ta/wq/arithmetic.py
CHANGED
@@ -1,10 +1,36 @@
|
|
1
1
|
import numpy as np
|
2
|
-
from polars import Expr, Series, fold, any_horizontal
|
2
|
+
from polars import Expr, Series, fold, any_horizontal, Float64
|
3
3
|
from polars import max_horizontal, sum_horizontal, min_horizontal, mean_horizontal
|
4
4
|
|
5
5
|
|
6
6
|
def abs_(x: Expr) -> Expr:
|
7
|
-
"""绝对值
|
7
|
+
"""绝对值
|
8
|
+
|
9
|
+
Examples
|
10
|
+
--------
|
11
|
+
```python
|
12
|
+
df = pl.DataFrame({
|
13
|
+
'a': [None, -1, 0, 1, 2],
|
14
|
+
'b': [None, -1, 0, 1, 2],
|
15
|
+
}).with_columns(
|
16
|
+
out1=abs_(pl.col('a')),
|
17
|
+
out2=abs_(-1),
|
18
|
+
)
|
19
|
+
shape: (5, 4)
|
20
|
+
┌──────┬──────┬──────┬──────┐
|
21
|
+
│ a ┆ b ┆ out1 ┆ out2 │
|
22
|
+
│ --- ┆ --- ┆ --- ┆ --- │
|
23
|
+
│ i64 ┆ i64 ┆ i64 ┆ i32 │
|
24
|
+
╞══════╪══════╪══════╪══════╡
|
25
|
+
│ null ┆ null ┆ null ┆ 1 │
|
26
|
+
│ -1 ┆ -1 ┆ 1 ┆ 1 │
|
27
|
+
│ 0 ┆ 0 ┆ 0 ┆ 1 │
|
28
|
+
│ 1 ┆ 1 ┆ 1 ┆ 1 │
|
29
|
+
│ 2 ┆ 2 ┆ 2 ┆ 1 │
|
30
|
+
└──────┴──────┴──────┴──────┘
|
31
|
+
```
|
32
|
+
|
33
|
+
"""
|
8
34
|
if isinstance(x, (Expr, Series)):
|
9
35
|
return x.abs()
|
10
36
|
else:
|
@@ -86,17 +112,92 @@ def densify(x: Expr) -> Expr:
|
|
86
112
|
|
87
113
|
|
88
114
|
def divide(x: Expr, y: Expr) -> Expr:
|
89
|
-
"""x/y
|
115
|
+
"""x/y
|
116
|
+
|
117
|
+
Examples
|
118
|
+
--------
|
119
|
+
```python
|
120
|
+
df = pl.DataFrame({
|
121
|
+
'a': [None, -1, 0, 1, 2],
|
122
|
+
'b': [None, -1, 0, 1, 2],
|
123
|
+
}).with_columns(
|
124
|
+
out1=divide(pl.col('a'), 0),
|
125
|
+
out2=divide(pl.col('a'), 1),
|
126
|
+
out3=divide(pl.col('a'), pl.col('b')),
|
127
|
+
)
|
128
|
+
shape: (5, 5)
|
129
|
+
┌──────┬──────┬──────┬──────┬──────┐
|
130
|
+
│ a ┆ b ┆ out1 ┆ out2 ┆ out3 │
|
131
|
+
│ --- ┆ --- ┆ --- ┆ --- ┆ --- │
|
132
|
+
│ i64 ┆ i64 ┆ f64 ┆ f64 ┆ f64 │
|
133
|
+
╞══════╪══════╪══════╪══════╪══════╡
|
134
|
+
│ null ┆ null ┆ null ┆ null ┆ null │
|
135
|
+
│ -1 ┆ -1 ┆ -inf ┆ -1.0 ┆ 1.0 │
|
136
|
+
│ 0 ┆ 0 ┆ NaN ┆ 0.0 ┆ NaN │
|
137
|
+
│ 1 ┆ 1 ┆ inf ┆ 1.0 ┆ 1.0 │
|
138
|
+
│ 2 ┆ 2 ┆ inf ┆ 2.0 ┆ 1.0 │
|
139
|
+
└──────┴──────┴──────┴──────┴──────┘
|
140
|
+
```
|
141
|
+
|
142
|
+
"""
|
90
143
|
return x / y
|
91
144
|
|
92
145
|
|
93
146
|
def exp(x: Expr) -> Expr:
|
94
|
-
"""自然指数函数
|
147
|
+
"""自然指数函数
|
148
|
+
|
149
|
+
Examples
|
150
|
+
--------
|
151
|
+
```python
|
152
|
+
df = pl.DataFrame({
|
153
|
+
'a': [None, -1, 0, 1, 2],
|
154
|
+
}).with_columns(
|
155
|
+
out1=expm1(pl.col('a')),
|
156
|
+
)
|
157
|
+
shape: (5, 2)
|
158
|
+
┌──────┬──────────┐
|
159
|
+
│ a ┆ out1 │
|
160
|
+
│ --- ┆ --- │
|
161
|
+
│ i64 ┆ f64 │
|
162
|
+
╞══════╪══════════╡
|
163
|
+
│ null ┆ null │
|
164
|
+
│ -1 ┆ 0.367879 │
|
165
|
+
│ 0 ┆ 1.0 │
|
166
|
+
│ 1 ┆ 2.718282 │
|
167
|
+
│ 2 ┆ 7.389056 │
|
168
|
+
└──────┴──────────┘
|
169
|
+
```
|
170
|
+
|
171
|
+
"""
|
95
172
|
return x.exp()
|
96
173
|
|
97
174
|
|
98
175
|
def expm1(x: Expr) -> Expr:
|
99
|
-
"""对数收益率 转 简单收益率 convert log return to simple return
|
176
|
+
"""对数收益率 转 简单收益率 convert log return to simple return
|
177
|
+
|
178
|
+
Examples
|
179
|
+
--------
|
180
|
+
```python
|
181
|
+
df = pl.DataFrame({
|
182
|
+
'a': [None, -1, 0, 1, 2],
|
183
|
+
}).with_columns(
|
184
|
+
out1=expm1(pl.col('a')),
|
185
|
+
)
|
186
|
+
shape: (5, 2)
|
187
|
+
┌──────┬───────────┐
|
188
|
+
│ a ┆ out1 │
|
189
|
+
│ --- ┆ --- │
|
190
|
+
│ i64 ┆ f64 │
|
191
|
+
╞══════╪═══════════╡
|
192
|
+
│ null ┆ null │
|
193
|
+
│ -1 ┆ -0.632121 │
|
194
|
+
│ 0 ┆ 0.0 │
|
195
|
+
│ 1 ┆ 1.718282 │
|
196
|
+
│ 2 ┆ 6.389056 │
|
197
|
+
└──────┴───────────┘
|
198
|
+
```
|
199
|
+
|
200
|
+
"""
|
100
201
|
return x.exp() - 1
|
101
202
|
|
102
203
|
|
@@ -147,12 +248,60 @@ def fraction(x: Expr) -> Expr:
|
|
147
248
|
|
148
249
|
|
149
250
|
def inverse(x: Expr) -> Expr:
|
150
|
-
"""1/x
|
251
|
+
"""1/x
|
252
|
+
|
253
|
+
Examples
|
254
|
+
--------
|
255
|
+
```python
|
256
|
+
df = pl.DataFrame({
|
257
|
+
'a': [None, -1, 0, 1, 2],
|
258
|
+
}).with_columns(
|
259
|
+
out1=inverse(pl.col('a')),
|
260
|
+
)
|
261
|
+
shape: (5, 2)
|
262
|
+
┌──────┬──────┐
|
263
|
+
│ a ┆ out1 │
|
264
|
+
│ --- ┆ --- │
|
265
|
+
│ i64 ┆ f64 │
|
266
|
+
╞══════╪══════╡
|
267
|
+
│ null ┆ null │
|
268
|
+
│ -1 ┆ -1.0 │
|
269
|
+
│ 0 ┆ inf │
|
270
|
+
│ 1 ┆ 1.0 │
|
271
|
+
│ 2 ┆ 0.5 │
|
272
|
+
└──────┴──────┘
|
273
|
+
```
|
274
|
+
|
275
|
+
"""
|
151
276
|
return 1 / x
|
152
277
|
|
153
278
|
|
154
279
|
def log(x: Expr) -> Expr:
|
155
|
-
"""e为底的对数
|
280
|
+
"""e为底的对数
|
281
|
+
|
282
|
+
Examples
|
283
|
+
--------
|
284
|
+
```python
|
285
|
+
df = pl.DataFrame({
|
286
|
+
'a': [None, -1, 0, 1, 2],
|
287
|
+
}).with_columns(
|
288
|
+
out1=log(pl.col('a')),
|
289
|
+
)
|
290
|
+
shape: (5, 2)
|
291
|
+
┌──────┬──────────┐
|
292
|
+
│ a ┆ out1 │
|
293
|
+
│ --- ┆ --- │
|
294
|
+
│ i64 ┆ f64 │
|
295
|
+
╞══════╪══════════╡
|
296
|
+
│ null ┆ null │
|
297
|
+
│ -1 ┆ NaN │
|
298
|
+
│ 0 ┆ -inf │
|
299
|
+
│ 1 ┆ 0.0 │
|
300
|
+
│ 2 ┆ 0.693147 │
|
301
|
+
└──────┴──────────┘
|
302
|
+
```
|
303
|
+
|
304
|
+
"""
|
156
305
|
if isinstance(x, (Expr, Series)):
|
157
306
|
return x.log()
|
158
307
|
else:
|
@@ -160,7 +309,31 @@ def log(x: Expr) -> Expr:
|
|
160
309
|
|
161
310
|
|
162
311
|
def log10(x: Expr) -> Expr:
|
163
|
-
"""10为底的对数
|
312
|
+
"""10为底的对数
|
313
|
+
|
314
|
+
Examples
|
315
|
+
--------
|
316
|
+
```python
|
317
|
+
df = pl.DataFrame({
|
318
|
+
'a': [None, -1, 0, 1, 2],
|
319
|
+
}).with_columns(
|
320
|
+
out1=log10(pl.col('a')),
|
321
|
+
)
|
322
|
+
shape: (5, 2)
|
323
|
+
┌──────┬─────────┐
|
324
|
+
│ a ┆ out1 │
|
325
|
+
│ --- ┆ --- │
|
326
|
+
│ i64 ┆ f64 │
|
327
|
+
╞══════╪═════════╡
|
328
|
+
│ null ┆ null │
|
329
|
+
│ -1 ┆ NaN │
|
330
|
+
│ 0 ┆ -inf │
|
331
|
+
│ 1 ┆ 0.0 │
|
332
|
+
│ 2 ┆ 0.30103 │
|
333
|
+
└──────┴─────────┘
|
334
|
+
```
|
335
|
+
|
336
|
+
"""
|
164
337
|
return x.log10()
|
165
338
|
|
166
339
|
|
@@ -168,6 +341,29 @@ def log1p(x: Expr) -> Expr:
|
|
168
341
|
"""简单收益率 转 对数收益率 convert simple return to log return
|
169
342
|
|
170
343
|
log(x+1)
|
344
|
+
|
345
|
+
Examples
|
346
|
+
--------
|
347
|
+
```python
|
348
|
+
df = pl.DataFrame({
|
349
|
+
'a': [None, -1, 0, 1, 2],
|
350
|
+
}).with_columns(
|
351
|
+
out1=log1p(pl.col('a')),
|
352
|
+
)
|
353
|
+
shape: (5, 2)
|
354
|
+
┌──────┬──────────┐
|
355
|
+
│ a ┆ out1 │
|
356
|
+
│ --- ┆ --- │
|
357
|
+
│ i64 ┆ f64 │
|
358
|
+
╞══════╪══════════╡
|
359
|
+
│ null ┆ null │
|
360
|
+
│ -1 ┆ -inf │
|
361
|
+
│ 0 ┆ 0.0 │
|
362
|
+
│ 1 ┆ 0.693147 │
|
363
|
+
│ 2 ┆ 1.098612 │
|
364
|
+
└──────┴──────────┘
|
365
|
+
```
|
366
|
+
|
171
367
|
"""
|
172
368
|
return x.log1p()
|
173
369
|
|
@@ -178,7 +374,33 @@ def max_(a: Expr, b: Expr, *args) -> Expr:
|
|
178
374
|
|
179
375
|
|
180
376
|
def mean(a: Expr, b: Expr, *args) -> Expr:
|
181
|
-
"""水平多列均值
|
377
|
+
"""水平多列均值
|
378
|
+
|
379
|
+
Examples
|
380
|
+
--------
|
381
|
+
```python
|
382
|
+
df = pl.DataFrame({
|
383
|
+
'a': [None, -1, 0, 1, 2],
|
384
|
+
'b': [None, -1, 0, 0, 2],
|
385
|
+
}).with_columns(
|
386
|
+
out2=mean(pl.col('a'), 2),
|
387
|
+
out3=mean(pl.col('a'), pl.col('b')),
|
388
|
+
)
|
389
|
+
shape: (5, 4)
|
390
|
+
┌──────┬──────┬──────┬──────┐
|
391
|
+
│ a ┆ b ┆ out2 ┆ out3 │
|
392
|
+
│ --- ┆ --- ┆ --- ┆ --- │
|
393
|
+
│ i64 ┆ i64 ┆ f64 ┆ f64 │
|
394
|
+
╞══════╪══════╪══════╪══════╡
|
395
|
+
│ null ┆ null ┆ 2.0 ┆ null │
|
396
|
+
│ -1 ┆ -1 ┆ 0.5 ┆ -1.0 │
|
397
|
+
│ 0 ┆ 0 ┆ 1.0 ┆ 0.0 │
|
398
|
+
│ 1 ┆ 0 ┆ 1.5 ┆ 0.5 │
|
399
|
+
│ 2 ┆ 2 ┆ 2.0 ┆ 2.0 │
|
400
|
+
└──────┴──────┴──────┴──────┘
|
401
|
+
```
|
402
|
+
|
403
|
+
"""
|
182
404
|
return mean_horizontal(a, b, *args)
|
183
405
|
|
184
406
|
|
@@ -188,7 +410,33 @@ def min_(a: Expr, b: Expr, *args) -> Expr:
|
|
188
410
|
|
189
411
|
|
190
412
|
def mod(x: Expr, y: Expr) -> Expr:
|
191
|
-
"""x%y
|
413
|
+
"""x%y
|
414
|
+
|
415
|
+
Examples
|
416
|
+
--------
|
417
|
+
```python
|
418
|
+
df = pl.DataFrame({
|
419
|
+
'a': [None, -1, 0, 1, 2],
|
420
|
+
'b': [None, -1, 0, 0, 2],
|
421
|
+
}).with_columns(
|
422
|
+
out2=mod(pl.col('a'), 2),
|
423
|
+
out3=mod(pl.col('a'), pl.col('b')),
|
424
|
+
)
|
425
|
+
shape: (5, 4)
|
426
|
+
┌──────┬──────┬──────┬──────┐
|
427
|
+
│ a ┆ b ┆ out2 ┆ out3 │
|
428
|
+
│ --- ┆ --- ┆ --- ┆ --- │
|
429
|
+
│ i64 ┆ i64 ┆ i64 ┆ i64 │
|
430
|
+
╞══════╪══════╪══════╪══════╡
|
431
|
+
│ null ┆ null ┆ null ┆ null │
|
432
|
+
│ -1 ┆ -1 ┆ 1 ┆ 0 │
|
433
|
+
│ 0 ┆ 0 ┆ 0 ┆ null │
|
434
|
+
│ 1 ┆ 0 ┆ 1 ┆ null │
|
435
|
+
│ 2 ┆ 2 ┆ 0 ┆ 0 │
|
436
|
+
└──────┴──────┴──────┴──────┘
|
437
|
+
```
|
438
|
+
|
439
|
+
"""
|
192
440
|
return x % y
|
193
441
|
|
194
442
|
|
@@ -234,8 +482,37 @@ def multiply(a: Expr, b: Expr, *args) -> Expr:
|
|
234
482
|
|
235
483
|
|
236
484
|
def power(x: Expr, y: Expr) -> Expr:
|
237
|
-
"""x ** y
|
238
|
-
|
485
|
+
"""x ** y
|
486
|
+
|
487
|
+
Examples
|
488
|
+
--------
|
489
|
+
```python
|
490
|
+
df = pl.DataFrame({
|
491
|
+
'a': [None, -1, 0, 1, 2],
|
492
|
+
'b': [None, -1, 0, 1, 2],
|
493
|
+
}).with_columns(
|
494
|
+
out2=power(pl.col('a'), 1),
|
495
|
+
out3=power(pl.col('a'), pl.col('b')),
|
496
|
+
)
|
497
|
+
shape: (5, 4)
|
498
|
+
┌──────┬──────┬──────┬──────┐
|
499
|
+
│ a ┆ b ┆ out2 ┆ out3 │
|
500
|
+
│ --- ┆ --- ┆ --- ┆ --- │
|
501
|
+
│ i64 ┆ i64 ┆ i64 ┆ f64 │
|
502
|
+
╞══════╪══════╪══════╪══════╡
|
503
|
+
│ null ┆ null ┆ null ┆ null │
|
504
|
+
│ -1 ┆ -1 ┆ -1 ┆ -1.0 │
|
505
|
+
│ 0 ┆ 0 ┆ 0 ┆ 1.0 │
|
506
|
+
│ 1 ┆ 1 ┆ 1 ┆ 1.0 │
|
507
|
+
│ 2 ┆ 2 ┆ 2 ┆ 4.0 │
|
508
|
+
└──────┴──────┴──────┴──────┘
|
509
|
+
```
|
510
|
+
|
511
|
+
"""
|
512
|
+
if isinstance(y, (int, float)):
|
513
|
+
return x.pow(y)
|
514
|
+
|
515
|
+
return x.pow(y.cast(Float64))
|
239
516
|
|
240
517
|
|
241
518
|
def reverse(x: Expr) -> Expr:
|
@@ -370,6 +647,31 @@ def sign(x: Expr) -> Expr:
|
|
370
647
|
def signed_power(x: Expr, y: Expr) -> Expr:
|
371
648
|
"""x raised to the power of y such that final result preserves sign of x.
|
372
649
|
|
650
|
+
Examples
|
651
|
+
--------
|
652
|
+
```python
|
653
|
+
df = pl.DataFrame({
|
654
|
+
'a': [None, -1, 0, 1, 2],
|
655
|
+
'b': [None, -1, 0, 1, 2],
|
656
|
+
}).with_columns(
|
657
|
+
out1=signed_power(pl.col('a'), 0),
|
658
|
+
out2=signed_power(pl.col('a'), 1),
|
659
|
+
out3=signed_power(pl.col('a'), pl.col('b')),
|
660
|
+
)
|
661
|
+
|
662
|
+
shape: (5, 5)
|
663
|
+
┌──────┬──────┬──────┬──────┬──────┐
|
664
|
+
│ a ┆ b ┆ out1 ┆ out2 ┆ out3 │
|
665
|
+
│ --- ┆ --- ┆ --- ┆ --- ┆ --- │
|
666
|
+
│ i64 ┆ i64 ┆ i64 ┆ i64 ┆ f64 │
|
667
|
+
╞══════╪══════╪══════╪══════╪══════╡
|
668
|
+
│ null ┆ null ┆ null ┆ null ┆ null │
|
669
|
+
│ -1 ┆ -1 ┆ -1 ┆ -1 ┆ -1.0 │
|
670
|
+
│ 0 ┆ 0 ┆ 0 ┆ 0 ┆ 0.0 │
|
671
|
+
│ 1 ┆ 1 ┆ 1 ┆ 1 ┆ 1.0 │
|
672
|
+
│ 2 ┆ 2 ┆ 1 ┆ 2 ┆ 4.0 │
|
673
|
+
└──────┴──────┴──────┴──────┴──────┘
|
674
|
+
```
|
373
675
|
|
374
676
|
References
|
375
677
|
----------
|
@@ -382,7 +684,7 @@ def signed_power(x: Expr, y: Expr) -> Expr:
|
|
382
684
|
elif y == 0:
|
383
685
|
return x.sign()
|
384
686
|
|
385
|
-
return x.abs().pow(y) * x.sign()
|
687
|
+
return x.abs().pow(y.cast(Float64)) * x.sign()
|
386
688
|
|
387
689
|
|
388
690
|
def sin(x: Expr) -> Expr:
|
@@ -396,7 +698,32 @@ def sinh(x: Expr) -> Expr:
|
|
396
698
|
|
397
699
|
|
398
700
|
def softsign(x: Expr) -> Expr:
|
399
|
-
"""softsign是 tanh激活函数的另一个替代选择
|
701
|
+
"""softsign是 tanh激活函数的另一个替代选择
|
702
|
+
|
703
|
+
Examples
|
704
|
+
--------
|
705
|
+
```python
|
706
|
+
df = pl.DataFrame({
|
707
|
+
'a': [None, -1, 0, 1, 2],
|
708
|
+
}).with_columns(
|
709
|
+
out1=softsign(pl.col('a')),
|
710
|
+
)
|
711
|
+
|
712
|
+
shape: (5, 2)
|
713
|
+
┌──────┬──────────┐
|
714
|
+
│ a ┆ out1 │
|
715
|
+
│ --- ┆ --- │
|
716
|
+
│ i64 ┆ f64 │
|
717
|
+
╞══════╪══════════╡
|
718
|
+
│ null ┆ null │
|
719
|
+
│ -1 ┆ -0.5 │
|
720
|
+
│ 0 ┆ 0.0 │
|
721
|
+
│ 1 ┆ 0.5 │
|
722
|
+
│ 2 ┆ 0.666667 │
|
723
|
+
└──────┴──────────┘
|
724
|
+
```
|
725
|
+
|
726
|
+
"""
|
400
727
|
return x / (1 + x.abs())
|
401
728
|
|
402
729
|
|
@@ -411,23 +738,126 @@ def subtract(x: Expr, y: Expr) -> Expr:
|
|
411
738
|
|
412
739
|
|
413
740
|
def tan(x: Expr) -> Expr:
|
414
|
-
"""正切
|
741
|
+
"""正切
|
742
|
+
|
743
|
+
Examples
|
744
|
+
--------
|
745
|
+
```python
|
746
|
+
df = pl.DataFrame({
|
747
|
+
'a': [None, -1, 0, 1, 2],
|
748
|
+
}).with_columns(
|
749
|
+
out1=tan(pl.col('a')),
|
750
|
+
)
|
751
|
+
|
752
|
+
shape: (5, 2)
|
753
|
+
┌──────┬───────────┐
|
754
|
+
│ a ┆ out1 │
|
755
|
+
│ --- ┆ --- │
|
756
|
+
│ i64 ┆ f64 │
|
757
|
+
╞══════╪═══════════╡
|
758
|
+
│ null ┆ null │
|
759
|
+
│ -1 ┆ -1.557408 │
|
760
|
+
│ 0 ┆ 0.0 │
|
761
|
+
│ 1 ┆ 1.557408 │
|
762
|
+
│ 2 ┆ -2.18504 │
|
763
|
+
└──────┴───────────┘
|
764
|
+
```
|
765
|
+
|
766
|
+
"""
|
415
767
|
return x.tan()
|
416
768
|
|
417
769
|
|
418
770
|
def tanh(x: Expr) -> Expr:
|
419
|
-
"""双曲正切
|
771
|
+
"""双曲正切
|
772
|
+
|
773
|
+
Examples
|
774
|
+
--------
|
775
|
+
```python
|
776
|
+
df = pl.DataFrame({
|
777
|
+
'a': [None, -1, 0, 1, 2],
|
778
|
+
}).with_columns(
|
779
|
+
out1=tanh(pl.col('a')),
|
780
|
+
)
|
781
|
+
|
782
|
+
shape: (5, 2)
|
783
|
+
┌──────┬───────────┐
|
784
|
+
│ a ┆ out1 │
|
785
|
+
│ --- ┆ --- │
|
786
|
+
│ i64 ┆ f64 │
|
787
|
+
╞══════╪═══════════╡
|
788
|
+
│ null ┆ null │
|
789
|
+
│ -1 ┆ -0.761594 │
|
790
|
+
│ 0 ┆ 0.0 │
|
791
|
+
│ 1 ┆ 0.761594 │
|
792
|
+
│ 2 ┆ 0.964028 │
|
793
|
+
└──────┴───────────┘
|
794
|
+
```
|
795
|
+
|
796
|
+
"""
|
420
797
|
return x.tanh()
|
421
798
|
|
422
799
|
|
423
800
|
def var(a: Expr, b: Expr, *args) -> Expr:
|
424
|
-
"""水平多列方差
|
801
|
+
"""水平多列方差
|
802
|
+
|
803
|
+
Examples
|
804
|
+
--------
|
805
|
+
```python
|
806
|
+
df = pl.DataFrame({
|
807
|
+
'a': [None, -1, 1, 1, 2],
|
808
|
+
'b': [None, -1, 0, 1, 2],
|
809
|
+
'c': [None, -1, 0, 2, None],
|
810
|
+
}).with_columns(
|
811
|
+
out1=var(pl.col('a'), pl.col('b'), pl.col('c')),
|
812
|
+
)
|
813
|
+
|
814
|
+
shape: (5, 4)
|
815
|
+
┌──────┬──────┬──────┬──────────┐
|
816
|
+
│ a ┆ b ┆ c ┆ out1 │
|
817
|
+
│ --- ┆ --- ┆ --- ┆ --- │
|
818
|
+
│ i64 ┆ i64 ┆ i64 ┆ f64 │
|
819
|
+
╞══════╪══════╪══════╪══════════╡
|
820
|
+
│ null ┆ null ┆ null ┆ 0.0 │
|
821
|
+
│ -1 ┆ -1 ┆ -1 ┆ 0.0 │
|
822
|
+
│ 1 ┆ 0 ┆ 0 ┆ 0.666667 │
|
823
|
+
│ 1 ┆ 1 ┆ 2 ┆ 0.666667 │
|
824
|
+
│ 2 ┆ 2 ┆ null ┆ 0.0 │
|
825
|
+
└──────┴──────┴──────┴──────────┘
|
826
|
+
```
|
827
|
+
|
828
|
+
"""
|
425
829
|
_args = [a, b] + list(args)
|
426
830
|
_mean = mean_horizontal(_args)
|
427
|
-
|
428
|
-
return _sum
|
831
|
+
return sum_horizontal([(expr - _mean) ** 2 for expr in _args])
|
429
832
|
|
430
833
|
|
431
834
|
def std(a: Expr, b: Expr, *args) -> Expr:
|
432
|
-
"""水平多列标准差
|
835
|
+
"""水平多列标准差
|
836
|
+
|
837
|
+
Examples
|
838
|
+
--------
|
839
|
+
```python
|
840
|
+
df = pl.DataFrame({
|
841
|
+
'a': [None, -1, 1, 1, 2],
|
842
|
+
'b': [None, -1, 0, 1, 2],
|
843
|
+
'c': [None, -1, 0, 2, None],
|
844
|
+
}).with_columns(
|
845
|
+
out2=std(pl.col('a'), pl.col('b'), pl.col('c')),
|
846
|
+
)
|
847
|
+
|
848
|
+
shape: (5, 4)
|
849
|
+
┌──────┬──────┬──────┬──────────┐
|
850
|
+
│ a ┆ b ┆ c ┆ out2 │
|
851
|
+
│ --- ┆ --- ┆ --- ┆ --- │
|
852
|
+
│ i64 ┆ i64 ┆ i64 ┆ f64 │
|
853
|
+
╞══════╪══════╪══════╪══════════╡
|
854
|
+
│ null ┆ null ┆ null ┆ 0.0 │
|
855
|
+
│ -1 ┆ -1 ┆ -1 ┆ 0.0 │
|
856
|
+
│ 1 ┆ 0 ┆ 0 ┆ 0.816497 │
|
857
|
+
│ 1 ┆ 1 ┆ 2 ┆ 0.816497 │
|
858
|
+
│ 2 ┆ 2 ┆ null ┆ 0.0 │
|
859
|
+
└──────┴──────┴──────┴──────────┘
|
860
|
+
```
|
861
|
+
|
862
|
+
"""
|
433
863
|
return var(a, b, *args).sqrt()
|
polars_ta/wq/cross_sectional.py
CHANGED
@@ -198,6 +198,16 @@ def cs_fill_except_all_null(x: Expr, value=0) -> Expr:
|
|
198
198
|
return when(x.is_not_null().sum() == 0).then(x).otherwise(x.fill_null(value))
|
199
199
|
|
200
200
|
|
201
|
+
def cs_fill_mean(x: Expr) -> Expr:
|
202
|
+
"""填充`null`为均值"""
|
203
|
+
return x.fill_null(strategy='mean')
|
204
|
+
|
205
|
+
|
206
|
+
def cs_fill_null(x: Expr, value=0) -> Expr:
|
207
|
+
"""填充`null`为`value`"""
|
208
|
+
return x.fill_null(value)
|
209
|
+
|
210
|
+
|
201
211
|
def cs_regression_neut(y: Expr, x: Expr) -> Expr:
|
202
212
|
"""一元回归残差"""
|
203
213
|
return pls.compute_least_squares(y, x, add_intercept=True, mode='residuals', ols_kwargs=_ols_kwargs)
|
polars_ta/wq/time_series.py
CHANGED
@@ -484,9 +484,42 @@ def ts_delta(x: Expr, d: int = 1) -> Expr:
|
|
484
484
|
return x.diff(d)
|
485
485
|
|
486
486
|
|
487
|
-
def ts_fill_null(x: Expr) -> Expr:
|
488
|
-
"""用上一个非空值填充空值
|
489
|
-
|
487
|
+
def ts_fill_null(x: Expr, limit: int = None) -> Expr:
|
488
|
+
"""用上一个非空值填充空值
|
489
|
+
|
490
|
+
Parameters
|
491
|
+
----------
|
492
|
+
x
|
493
|
+
limit
|
494
|
+
最大填充次数
|
495
|
+
|
496
|
+
Examples
|
497
|
+
--------
|
498
|
+
```python
|
499
|
+
df = pl.DataFrame({
|
500
|
+
'a': [None, -1, 1, None, None],
|
501
|
+
'b': [None, True, False, None, None],
|
502
|
+
}).with_columns(
|
503
|
+
out1=ts_fill_null(pl.col('a')),
|
504
|
+
out2=ts_fill_null(pl.col('b'), 1),
|
505
|
+
)
|
506
|
+
|
507
|
+
shape: (5, 4)
|
508
|
+
┌──────┬───────┬──────┬───────┐
|
509
|
+
│ a ┆ b ┆ out1 ┆ out2 │
|
510
|
+
│ --- ┆ --- ┆ --- ┆ --- │
|
511
|
+
│ i64 ┆ bool ┆ i64 ┆ bool │
|
512
|
+
╞══════╪═══════╪══════╪═══════╡
|
513
|
+
│ null ┆ null ┆ null ┆ null │
|
514
|
+
│ -1 ┆ true ┆ -1 ┆ true │
|
515
|
+
│ 1 ┆ false ┆ 1 ┆ false │
|
516
|
+
│ null ┆ null ┆ 1 ┆ false │
|
517
|
+
│ null ┆ null ┆ 1 ┆ null │
|
518
|
+
└──────┴───────┴──────┴───────┘
|
519
|
+
```
|
520
|
+
|
521
|
+
"""
|
522
|
+
return x.forward_fill(limit)
|
490
523
|
|
491
524
|
|
492
525
|
def ts_ir(x: Expr, d: int = 1) -> Expr:
|