在python中反转顺序

Xip*_*ias 6 python currying toolz

假设我有这样的函数:

from toolz.curried import *

@curry
def foo(x, y):
    print(x, y)
Run Code Online (Sandbox Code Playgroud)

然后我可以打电话:

foo(1,2)
foo(1)(2)
Run Code Online (Sandbox Code Playgroud)

两者都返回预期的相同.

但是,我想做这样的事情:

@curry.inverse # hypothetical
def bar(*args, last):
    print(*args, last)

bar(1,2,3)(last)
Run Code Online (Sandbox Code Playgroud)

这背后的想法是我想预先配置一个函数,然后把它放在这样的管道中:

pipe(data,
    f1, # another function
    bar(1,2,3) # unknown number of arguments
)
Run Code Online (Sandbox Code Playgroud)

然后,bar(1,2,3)(data)将被称为管道的一部分.但是,我不知道该怎么做.有任何想法吗?非常感谢你!

编辑:

要求提供一个更具说明性的例子.因此,它来了:

import pandas as pd
from toolz.curried import *

df = pd.DataFrame(data)

def filter_columns(*args, df):
    return df[[*args]]

pipe(df,
    transformation_1,
    transformation_2,
    filter_columns("date", "temperature")
)
Run Code Online (Sandbox Code Playgroud)

正如您所看到的,DataFrame通过函数传递,并且filter_columns就是其中之一.但是,该函数已预先配置并返回一个只接受DataFrame的函数,类似于装饰器.这可以实现相同的行为:

def filter_columns(*args):
    def f(df):
        return df[[*args]]
    return f
Run Code Online (Sandbox Code Playgroud)

但是,我总是要运行两个调用,例如filter_columns()(df),这就是我想要避免的.

Cop*_*eld 2

好吧,我不熟悉 toolz 模块,但看起来没有简单的方法来柯里化具有任意数量参数的函数,所以让我们尝试其他方法。

首先作为替代

def filter_columns(*args):
    def f(df):
        return df[*args]
    return f
Run Code Online (Sandbox Code Playgroud)

(顺便说一下,df[*args]这是一个语法错误)

为了避免filter_columns()(data)您可以只抓取最后一个元素args并使用切片符号来抓取其他所有内容,例如

def filter_columns(*argv):
    df, columns = argv[-1], argv[:-1]
    return df[columns]
Run Code Online (Sandbox Code Playgroud)

并使用 as filter_columns(df)filter_columns("date", "temperature", df)等。

然后使用functools.partial构建新的、部分应用的过滤器来构建管道,例如

from functools import partial
from toolz.curried import pipe # always be explicit with your import, the last thing you want is import something you don't want to, that overwrite something else you use

pipe(df,
    transformation_1,
    transformation_2,
    partial(filter_columns, "date", "temperature")
)
Run Code Online (Sandbox Code Playgroud)