2007-12-24 / 13:19 / dave

The cast

dataset
An object for handling table-like data
dataset2
Version 2
dsutils
Utility functions for dataset
dsutils2
utility functions for dataset2

Act I

# dsutils2.py
from dataset2 import Dataset2
import dsutils as dsutils1
row2col2 = lambda ds2, *a, **ka: \
     Dataset2.from_dataset1(dsutils1.row2col(ds2.as_dataset1(), *a, **ka))
col2row2 = lambda ds2, *a, **ka: \
     Dataset2.from_dataset1(dsutils1.col2row(ds2.as_dataset1(), *a, **ka))

Act II

# dsutils2.py
# same
wrap_ds1f = lambda f: lambda ds2, *a, **ka: \
    Dataset2.from_dataset1(f(ds2.as_dataset1(), *a, **ka))
row2col2 = wrap_ds1f(dsutils1.row2col)
col2row2 = wrap_ds1f(dsutils1.col2row)
# in interpreter
>>> import(dsutils2)
>>> help(dsutils2)
Help on module dsutils2:
...
    col2row2 lambda ds2, *a, **ka
    ...
    row2col2 lambda ds2, *a, **ka
    ...
    wrap_ds1f lambda f
...
# That's not very helpful

Act III

def wrap_ds1func(ds1_func):
    """Create a wrapper for a function that accepts a dataset1 as it's first
    argument.  This creates a wrapper that converts a dataset2 into a
    dataset1, runs the function and converts the result  back to a dataset2.
    """
    def ds2_func(ds2, *args, **kargs):
        return Dataset.from_dataset1(
            ds1_func(ds2.to_dataset1(), *args, **kargs))
    ds2_func.__name__ = "%s2" % ds1_func.__name__
    ds2_func.__doc__ = "dataset2 version of %s, orig docs below.\n%s" \
                       % (ds1_func.__name__, ds1_func.__doc__)
    return ds2_func

row2col2 = wrap_ds1func(dsutils1.row2col)
col2row2 = wrap_ds1func(dsutils1.col2row)
# in interpreter
# same
Help on module dsutils2:
...
    col2row2 = col2row2(ds, *args, **kargs)
        dataset2 version of col2row, orig docs below.
        Convert a row with several columns into several rows with...
    row2col2 = row2col2(ds, *args, **kargs)
        dataset2 version of row2col, orig docs below.
        Convert several rows with related values into a single row with...
    wrap_ds1func(ds1_func)
        Create a wrapper for a function that accepts a dataset1 as it's first...
...
# better!

Epilogue

Longer, but reusable. And with readable help. Is it worth it? We’ll see. Either way higher order functions sure are nice.