def _sieve(): yield 1 candidates = Stream(count(2)) while True: prime, rest = candidates.advance() yield prime candidates = candidates.filter(_make_filter(prime))
def test_max(): def first(seq): return seq[0] def second(seq): return seq[1] assert Stream([2, 1, 5, 4, -6]).max() == 5 s = Stream([('a', 2), ('z', 1), ('c', 7)]) assert s.max(key=first) == ('z', 1) assert s.max(key=second) == ('c', 7)
def caesar_cypher(message: str, shift: int) -> str: num_letters = (ord('z') - ord('a')) + 1 ascii_cycle = partials.compose3( partials.add(-ord('a')), partials.modulo(num_letters), partials.add(ord('a'))) return ''.join(Stream(message).map(ord).map(partials.add(shift)).map(ascii_cycle).map(chr))
def test_for_each(): def _side_effect(inc: int): global accum accum += inc Stream(count(1)).take(5).for_each(_side_effect) assert accum == 15
def caesar_cypher_with_special_chars(message: str, shift: int) -> str: a = ord('a') z = ord('z') num_letters = (z - a) + 1 ascii_cycle = partials.compose3( partials.add(-a), partials.modulo(num_letters), partials.add(a)) return ''.join(Stream(message).map(ord).map_if( condition=partials.is_in(range(a, z + 1)), func=partials.add(shift) ).map_if( condition=partials.is_in(range(a + shift, z + shift + 1)), func=ascii_cycle ).map(chr))
def sieve_eratosthenes() -> Stream[int]: def _make_filter( prime: int ): # HACK: Necessary because python closures are late-binding return lambda x: x % prime != 0 def _sieve(): yield 1 candidates = Stream(count(2)) while True: prime, rest = candidates.advance() yield prime candidates = candidates.filter(_make_filter(prime)) return Stream(_sieve())
def sieve_eratosthenes_pyfunctional() -> Stream[int]: def _make_filter( prime: int ): # HACK: Necessary because python closures are late-binding return lambda x: x % prime != 0 def _sieve(): yield 1 candidates = seq(count(2)) while True: prime = candidates.first() candidates.drop(1) yield prime candidates = candidates.filter(_make_filter(prime)) return Stream(_sieve())
def test_map(): assert Stream([1, 5, 3]).map(lambda x: x * 2).to_list() == [2, 10, 6]
def test_filter_when_items_are_tuples(): assert (Stream([('a', 1), ('b', 5), ('c', 3) ]).filter(lambda k, v: v > 3).to_list()) == [('b', 5)]
def test_map_when_items_are_tuples(): assert (Stream([('a', 1), ('b', 5), ('c', 3) ]).map(lambda k, v: (k, v * 2)).to_list()) == [('a', 2), ('b', 10), ('c', 6)]
def test_extend(): assert Stream([1, 2]).extend(3).to_list() == [1, 2, 3]
def test_append(): assert Stream([1, 2, 3]).append(0).to_list() == [0, 1, 2, 3]
def test_take(): assert Stream(count(1, 2)).take(3).to_list() == [1, 3, 5]
def test_to_list(): s = Stream(['a', 'b', 'c']) assert s.to_list() == ['a', 'b', 'c'] assert s.to_list() == ['a', 'b', 'c']
def test_zip(): ascii_a_to_c = range(ord('a'), ord('d')) assert Stream(cycle(ascii_a_to_c)).map(chr).zip( count(1)).take(5).to_list() == [('a', 1), ('b', 2), ('c', 3), ('a', 4), ('b', 5)]
def test_iter(): s = Stream([0, 1, 2, 3]) for i, x in zip(range(4), s): assert i == x
def test_filter(): assert Stream(count(1)).filter(lambda x: x % 7 == 0).take(4).to_list() == [ 7, 14, 21, 28 ]
def test_drop(): assert Stream(count(1, 2)).drop(3).first() == 7
def test_chain(): assert Stream([1, 2, 3]).chain(Stream( ['a', 'b', 'c']), count(4)).take(8).to_list() == [1, 2, 3, 'a', 'b', 'c', 4, 5]
def caesar_cypher2(message: str, shift: int) -> str: alphabet = 'abcdefghijklmnopqrstuvwxyz' return Stream(message).map_if( condition=_.is_in(alphabet), func=compose4(alphabet.find, _.add(shift), _.modulo(len(alphabet)), alphabet.__getitem__) ).join()
def test_first(): assert Stream([2, 1, 4]).first() == 2
def test_advance(): x, rest = Stream(count(3)).take(4).advance() assert x == 3 assert rest.to_list() == [4, 5, 6]
def test_reduce(): assert Stream([1, 2, 3, 4]).reduce(lambda k, v: k + v) == 10