如何在Snakemake流程中直接运行简短Python数据处理代码?
解决Snakemake中DataFrame滚动平均的高效实现方式
问题描述
我在Snakemake流程中需要对DataFrame应用滚动平均,尝试直接在rule的shell指令中编写Python代码但无法正常运行:
rule average_df: input: # script = , df_raw = "{sample}_raw.csv" params: window = 83 output: df_avg = "{sample}_avg.csv" shell: """ python import pandas as pd df=pd.read_csv("{input.df_raw}") df=df.rolling(window={params.window}, center=True, min_periods=1).mean() df.to_csv("{output.df_avg}") """
不想编写带argparse的繁琐独立脚本,询问是否有更智能高效的实现方式。
高效实现方法
方法1:修复shell指令中的Python调用
原来的shell代码无法运行是因为没有通过-c参数将代码传递给Python解释器,直接换行的代码会被shell当作独立命令执行。修正后无需独立脚本:
rule average_df: input: df_raw = "{sample}_raw.csv" params: window = 83 output: df_avg = "{sample}_avg.csv" shell: """ python -c " import pandas as pd df = pd.read_csv('{input.df_raw}') df = df.rolling(window={params.window}, center=True, min_periods=1).mean() df.to_csv('{output.df_avg}') " """
注意:如果路径包含空格,需要确保引号正确转义,或者改用单引号包裹路径。
方法2:使用Snakemake内置的script指令(推荐)
Snakemake支持直接在rule中内嵌Python脚本,通过snakemake对象直接访问输入、输出和参数,无需字符串替换,代码更简洁安全:
rule average_df: input: df_raw = "{sample}_raw.csv" params: window = 83 output: df_avg = "{sample}_avg.csv" script: """ import pandas as pd df = pd.read_csv(snakemake.input.df_raw) df = df.rolling(window=snakemake.params.window, center=True, min_periods=1).mean() df.to_csv(snakemake.output.df_avg) """
这种方式完全避免了shell层的引号问题,Snakemake会自动处理脚本的执行环境,是最推荐的方案。
方法3:简化独立脚本(若需复用)
如果确实需要独立脚本,无需使用argparse,用sys.argv直接接收参数即可大幅简化代码:
average_df.py:
import pandas as pd import sys def average_df(i_path, o_path, window): df = pd.read_csv(i_path) # 注意将window转为整数,因为sys.argv传入的是字符串 df = df.rolling(window=int(window), center=True, min_periods=1).mean() df.to_csv(o_path) if __name__ == "__main__": average_df(sys.argv[1], sys.argv[2], sys.argv[3])
对应的Snakemake规则:
rule average_df: input: df_raw = "{sample}_raw.csv" params: window = 83 output: df_avg = "{sample}_avg.csv" shell: "python average_df.py {input.df_raw} {output.df_avg} {params.window}"
内容的提问来源于stack exchange,提问作者Ulises Rey
相关产品推荐
相关产品推荐

