Search This Blog

Saturday, April 27, 2013

Custom magic function in IPython session

I needed some additional functionality when running my interactive ipython session. As ipython session is easily extendable with a help of custom python base functions I decided to write one as an example.

The function searches for the last outputed list object and creates variables for easy access (latest version can be found on github). Instead of typing l[_index_] you can simple tame l__index_. See the example below.
 
~/.config/ipython/profile_default/startup# cat rl.py

def object_name(obj, ret=None):
    g=globals()
    ret=[]
    obj_id=id(obj)
    for i in g.keys() :
        if id(g[i]) == obj_id :
            print i, g[i]
            ret.append(i)
    return ret


def rl (mylist=None, prefix=None, limit=7):
    prefix = prefix if prefix else "l"
    limit = limit if limit else 7

    aux=list(Out.keys()) # we want to make a copy
    aux.sort()
    aux.reverse()
    last_index = aux[0]

    if mylist == None :
        mylist = Out[last_index]
        mylist_name=In[last_index]

        if type(mylist) is not  list :
            for i in aux :
                # print i, Out[i],
                if type(Out[i]) is list :
                    mylist = Out[i]
                    mylist_name=In[i]
                    print("using last list object: %s" % mylist_name)
                    break
    else :
        mylist_name = filter( lambda x: not x.startswith("_"), object_name(l))

    if type(mylist) is not  list :
        print("can't find any list or specified object is not a list")
        return

    glo=globals()

    for k, val in enumerate(mylist) :
        if k <= limit :
            name=prefix+str(k)
            glo[name]=val
            print("created variable %s = %s" % (name, val) )
        else :
            print("list %s has %d elements but only 7 was printed" % ( mylist_name, len(mylist) ) )
            break

def rla (**kargs) :
  rl(prefix="a", **kargs)

def rlb (**kargs) :
  rl(prefix="b", **kargs)

print
print("auxiliary functions `rl` `rla` and `rlb` have been defined")

Example how this works
 
$ ipython='ipython  --colors Linux --autocall=2

In [17]: l=[1,2,3,1,2,3,1,2,3,1,2,3]

# instead of typing l[0] or l[1] etc we can now use this variables
In [18]: rl
-------> rl()
created variable l0 = 1
created variable l1 = 2
created variable l2 = 3
created variable l3 = 1
created variable l4 = 2
created variable l5 = 3
created variable l6 = 1
created variable l7 = 2
list l has 24 elements but only 7 was printed

In [2]: a=l    

In [6]: a
Out[6]: [1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3]

In [7]: rl(a)
__ [1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3]
_ [1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3]
a [1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3]
_6 [1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3]
_4 [1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3]
l [1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3]
created variable l0 = 1
created variable l1 = 2
created variable l2 = 3
created variable l3 = 1
created variable l4 = 2
created variable l5 = 3
created variable l6 = 1
created variable l7 = 2
list ['a', 'l'] has 12 elements but only 7 was printed

In [10]: a
Out[10]: [1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3]

In [11]: rlb
-------> rlb()
created variable b0 = 1
created variable b1 = 2
created variable b2 = 3
created variable b3 = 1
created variable b4 = 2
created variable b5 = 3
created variable b6 = 1
created variable b7 = 2
list a has 12 elements but only 7 was printed

References
  1. https://github.com/rtomaszewski/dotfiles
  2. http://rtomaszewski.blogspot.co.uk/2013/04/how-to-find-list-variable-name.html
  3. http://en.wikipedia.org/wiki/Reflection_(computer_science)
  4. http://en.wikipedia.org/wiki/Type_introspection

No comments:

Post a Comment