-
Notifications
You must be signed in to change notification settings - Fork 1
/
join.py
49 lines (37 loc) · 1.19 KB
/
join.py
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
from functools import partial
class join:
r"""Wrap a generator with str.join.
>>> @join.on('\n')
... def lines(**kwargs):
... for k, v in kwargs.items():
... yield f'{k}={v}'
>>> print(lines(foo='bar', ayy='lmao'))
foo=bar
ayy=lmao
Automatically coerces yielded values to strings:
>>> join(range)(10)
'0123456789'
Also works as a method decorator:
>>> class Fancy(dict):
... @join.on('\n')
... def __repr__(self):
... yield type(self).__name__
... for key in self:
... yield f' {key}: {self[key]}'
>>> Fancy(a=1, b=2)
Fancy
a: 1
b: 2
"""
def __init__(self, func, sep=''):
self.func = func
self.sep = sep
@classmethod
def on(cls, sep):
return partial(cls, sep=sep)
def __call__(*args, **kwargs):
self, *args = args
return self.sep.join(map(str, self.func(*args, **kwargs)))
def __get__(self, instance, owner=None):
"""Mimic FunctionType's behavior to work as a method decorator."""
return partial(self, instance)