#1
  1. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jul 2013
    Posts
    13
    Rep Power
    0

    Is there a more pythonisque/general way to do this


    Hello,

    I am relatively new to python and have been using python along with numpy and scipy packages to do some scientific computing.

    I am working with data that is typically multidimensional anything from 1-D to 5-D. I used to program in C++ before and what I typically used to do was implement code seperately for handling each case, which is tedious and a maintainance nightmare.

    Here, is a simple code that I wrote in python that does interpolation of 3D images (numpy array) using scipy. I am only quoting the relevant bits

    Code:
    # Since the images are 3D, we have 3D deformation fields:
    X = deformation.data[0]
    Y = deformation.data[1]
    Z = deformation.data[2]
    
    # The size of the image we need to interpolate.
    # Note, the image is 3D. hence, we have vx, vy, vz.
    [vx, vy, vz] = image.getVolumeExtent();
    X = X.reshape([vx, vy, vz], order='F')
    Y = Y.reshape([vx, vy, vz], order='F')
    Z = Z.reshape([vx, vy, vz], order='F')
    
    # And now interpolate using numpy
    ndimage.map_coordinates(image.data, [Z, Y, X], result.data, order=self.order, prefilter=False)
    Now, if I want to convert it to 2D, then we have something like:
    Code:
    # Since the images are 2D, we have 2D deformation fields:
    X = deformation.data[0]
    Y = deformation.data[1]
    
    # The size of the image we need to interpolate.
    # Note, the image is 2D. hence, we have vx, vy.
    [vx, vy] = image.getVolumeExtent();
    X = X.reshape([vx, vy], order='F')
    Y = Y.reshape([vx, vy], order='F')
    # And now interpolate using numpy
    ndimage.map_coordinates(image.data, [Y, X], result.data, order=self.order, prefilter=False)
    So, I have to either use 'if' statements or implement different methods by finding out the dimensionality of the input data and then calling the relevant implementation.

    I was wondering if there is some mechanism in python that I can exploit which will allow me to have one function but still deal with this without writing many 'if' clauses, which will make the code a bit of a mess to manage.

    Many thanks for any help you can give me.

    Luca
  2. #2
  3. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    May 2013
    Location
    Usually Japan when not on contract
    Posts
    240
    Rep Power
    11
    There are a few weird points, like you never actually labeled the list [vx, vy, vz] so I'm not really sure I understand the nature of image.getVolumeExtent(), but basically this sort of thing is what is common in Python:
    python Code:
    def foo(deform):
        vol_ext = image.getVolumeExtent()
        def_data = [z.reshape(vol_ext, order='F') for z in deform]
        ndimage.map_coordinates(image.data, def_data, result.data, order=self.order, prefilter=False)
     
    foo(deformation.data)

    List comprehensions and a few other functional techniques can greatly reduce the workload when you have a clearly established procedure you need to express with a variable input. The inputs can be functions themselves and get relabeled within the function, so if the pattern is applicable to other procedures over the data, then you can expand this to
    python Code:
    def foo(deform, image_proc, image_map):
        vol_ext = image_proc()
        def_data = [z.reshape(vol_ext, order='F') for z in deform]
        image_map(image.data, def_data, result.data, order=self.order, prefilter=False)
     
    foo(deformation.data, image.getVolumeExtent, ndimage.map_coordinates)

    The lack of labels leads me to believe that the things your calling have side effects (perhaps global?) that you rely on. Normally to keep unexpected behavior to a minimum it is best to design functional procedures like these around functions that actually return a value, but that gets into another discussion entirely...

    Note the lack of parens on the arguments passed to foo() in the second example. We're passing the underlying functions/methods, not executing them in the argument list.

    Comments on this post

    • pamparana agrees : Incredibly helpful!
  4. #3
  5. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jul 2013
    Posts
    13
    Rep Power
    0
    Thank you!

    This "List Comprehension stuff" is really powerful. I had no idea such functional programming constructs existed in Python. I will look through a formal tutorial of the language at some point.
  6. #4
  7. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    May 2013
    Location
    Usually Japan when not on contract
    Posts
    240
    Rep Power
    11
    Just check the main Python docs. Its one of the only languages I can think of that have discoverable and thorough documentations.

    There isn't a lot of focus on FP in Python, though, so even where the language supports it you won't often find an overabundance of FP treatments in Python. Also, some weird-seeming (in light of what's possible/permissible in Python) FP omissions exist, like a deliberate lack of tail-recursive function optimization (recursion depth always leaves a stack trail, with a max depth of 1000 -- (>.<) !). As you get to know Python better it becomes useful to read the debates within the community and especially with Guido Hisself over such issues to get a grip on what he feels is pythonic VS what is convenient for the small minority of us who feel lisp and Haskell are Good Things. These debates often manifest in PEPs, so when you see "PEP" pay attention, its like a more conversational version of an RFC in the networking community.

    I don't agree with everything in Python, but I have to say that Guido has definitely expressed a clear vision; and its obvious in how "pythonic" code tends to be prose-like readable, even to outsiders (which is amazing when you think of it...).

    Comments on this post

    • pamparana agrees
    Last edited by zxq9; July 19th, 2013 at 09:59 AM.

IMN logo majestic logo threadwatch logo seochat tools logo