Package: hawkweed
Yet another implementation of missing functions.Installationpip install hawkweedUsagehawkweed is roughly divided into three different parts: datatypes, monads and
functions. All the functions are exhaustively documented with pydoc, all the
parameters, the functions’ time complexity (if applicable) and the return value
are given.DatatypesMost of the datatypes implemented in hawkweed are mere wrappers around Python
standard datatypes. If the function does not return anything in the Python
datatype, this implementation will returnselfto allow for chaining.A notable exception is the largely unstable and undocumentedFutureclass.fromhawkweedimportList,Dict,SetList([1]).append(2).extend([3,None,4]).remove_empty()# => List([1, 2, 3, 4])List(range(10)).take(5)# => generator from 0 to 4List(range(10)).drop(5)# => generator from 5 to 9List(range(10)).take_while(lambdax:x<5)# => generator from 0 to 4List(range(10)).drop_while(lambdax:x<5)# => generator from 4 to 9List(range(10)).nth(3)# => generator yielding 0, 3, 6 and 9 (lazily); works with any subclass of IterableList(range(10)).reset(range(5))# => List([0, 1, 2, 3, 4])Dict({1:2,3:4}).reverse()# => Dict({2: 1, 4: 3})Dict({1:2,3:4,2:None}).remove_empty()# => Dict({1: 2, 3: 4})Dict({1:2,3:4,None:"go away"}).remove_empty(filter_keys=True)# => Dict({1: 2, 3: 4})Dict({1:2,3:4,2:3}).remove_empty(fun=lambdax:x!=2)# => Dict({1: 2, 3: 4})Dict({1:2,3:4}).reduce(fun=lambdaacc,k,v:acc+k+v,acc=0)# => 10Dict({1:2,3:4}).reduce(fun=lambdaacc,k,v:acc+(k,v))# => (1, 2, 3, 4)Dict({1:2,3:4,5:6}).pick(1,5)# => Dict({1: 2, 5: 6})Set({1,2,3,4}).remove_empty(fun=lambdax:x!=3)# => Set({1, 2, 4})# And now for something completely differentDict({"foo":List([1,2,3,Dict({"bar":"baz"})])}).get_in("foo",3,"bar")# => "baz"Dict({"foo":List([1,2,3,Dict({"bar":"baz"})])}).get_in("foo",100,"bar")# => NoneDict({"foo":List([1,2,3,Dict({"bar":"baz"})])}).get_in("foo",100,"bar",dflt="i am a default value")# => "i am a default value"Dict({"foo":List([1,2,3,Dict({"bar":"baz"})])}).update_in("foo",1,"bar",to="update")# => Dict({"foo": List([1, 2, 3, Dict({"bar": "update"})])})# if you want to insert your own datatype, just inherit from hawkweed.Collection# and implement get(key, dflt=None) and __setitem__FunctionsAll of the functions are standalone and curried whenever possible. They do not depend
on hawkweeds datatypes in any way.fromhawkweedimportmap,reduce,List,all,any,constantly,delaymap(inc,range(100))# => range(1, 101)incrementor=map(inc)incrementor(List(range(100)))# => range(1, 101)summator=reduce(add)summator(range(5))# => 10all(lambdax:x>100,[101,102,103])# => Trueany(lambdax:x>10,[3,5,8])# => Falseconstantly(10)# => an infinite generator of 10delayed=delay(print,'Hello, World!')# => this will return a variable that, when called, will compute the result of print with the argument 'Hello, World!'# it will cache the result instead of recomputing it upon reevaluation, i.e. `delayed() or delayed()` will only print 'Hello, World!' onceA few other functions that you might expect from a functional programming library (compose,pipe,identity,apply,flip,curryand the like) are also implemented. They
should be intuitive and work as expected. If they do not or are not consider it a bug.MonadsThe implemented monads are: Identity, Maybe (Just/Nothing), Continuation, Either, IO, CachedIO,
and List (called ListM). do notation is also supported.fromhawkweedimportdoM,wrapM,JustdefdoMe():res1=yieldJust(1)res2=yieldJust(10)yieldJust(res1+res2)doM(doMe())# => Just(11)wrapM(Just(10)).real# => 10; the wrapper will try to call the wrapped values' function whenever it does not exist in the monadThere is a callcc function and all of the functions in Haskell’sData.MaybeandData.Eitherare implemented.Have fun!