关于
If I were doing this directly at the command line, I'd "source" a scriptcalled mySetUpFreeSurfer.sh that does nothing but set three environmentvariables, and then "source" another script, FreeSurferEnv.sh.
我想你会过得更好用Python编写自动化shell脚本的过程
newscript.sh,然后调用该脚本与 一个 电话
subprocess.check_output(而不是多次调用
Popen,
check_output,
call,等):
newscript.sh:
#!/bin/bashsource ~/scripts/mySetUpFreeSurfer.shsource /usr/local/freesurfer/FreeSurferEnv.shrecon-all -i /media/foo/bar -subjid s1001...
然后打电话
subprocess.check_output(['newscript.sh'])
import subprocessimport tempfileimport osimport statwith tempfile.NamedTemporaryFile(mode='w', delete=False) as f: f.write('''#!/bin/bashsource ~/scripts/mySetUpFreeSurfer.shsource /usr/local/freesurfer/FreeSurferEnv.sh''') root = "/media/foo/" for sub_dir in os.listdir(root): sub = "s" + sub_dir[0:4] anat_dir = os.path.join(root, sub_dir, "anatomical") for directory in os.listdir(anat_dir): time_dir = os.path.join(anat_dir, directory) for d in os.listdir(time_dir): dicoms_dir = os.path.join(time_dir, d, 'dicoms') dicom_list = os.listdir(dicoms_dir) dicom = dicom_list[0] path = os.path.join(dicoms_dir, dicom) cmd1 = "recon-all -i {} -subjid {}n".format(path, sub) f.write(cmd1) cmd2 = "recon-all -all -subjid {}n".format(sub) f.write(cmd2)filename = f.nameos.chmod(filename, stat.S_IRUSR | stat.S_IXUSR)subprocess.call([filename])os.unlink(filename)顺便说说,
def source(script, update=1): pipe = Popen(". %s; env" % script, stdout=PIPE, shell=True) data = pipe.communicate()[0] env = dict((line.split("=", 1) for line in data.splitlines())) if update: os.environ.update(env) return env被打破。例如,如果
script包含类似
VAR=`ls -1`export VAR
然后
. script; env
可能会像
VAR=file1file2file3
这将导致
source(script)提高
ValueError:
env = dict((line.split("=", 1) for line in data.splitlines()))ValueError: dictionary update sequence element #21 has length 1; 2 is required有一种解决方法
source:
env使用零字节的单独环境变量代替歧义的换行符:
def source(script, update=True): """ http://pythonwise.blogspot.fr/2010/04/sourcing-shell-script.html (Miki Tebeka) http://stackoverflow.com/questions/3503719/#comment28061110_3505826 (ahal) """ import subprocess import os proc = subprocess.Popen( ['bash', '-c', 'set -a && source {} && env -0'.format(script)], stdout=subprocess.PIPE, shell=False) output, err = proc.communicate() output = output.depre('utf8') env = dict((line.split("=", 1) for line in output.split('x00') if line)) if update: os.environ.update(env) return env但是,无论是否可修复,构造一个综合性的shell脚本(如上所示)仍然比解析
env并将
envdict传递给
subprocess调用更好。



