我可以在`%% bash`或`%% script` ipython笔记本单元格中访问python变量吗?

dre*_*cko 50 ipython-notebook ipython-magic

有没有办法从一个%%bash或其他%%script单元格中访问当前python内核中的变量?

也许作为命令行参数或环境变量?

dre*_*cko 63

Python变量可以在一个%%bash%%script单元格的第一行中访问,因此可以作为命令行参数传递给脚本.例如,使用bash,您可以执行以下操作:

%%bash -s "$myPythonVar" "$myOtherVar"
echo "This bash script knows about $1 and $2"
Run Code Online (Sandbox Code Playgroud)

-s命令行选项,可以通过位置参数bash中,通过访问$n用于第n个位置参数.请注意,实际分配给bash位置变量的是结果str(myPythonVariable).如果您传递包含引号字符(或其他bash敏感字符)的字符串,则需要使用反斜杠(例如:)来转义它们\".

该报价是很重要的-没有他们的蟒蛇变量(字符串表示)上的空间被分割,因此,如果myPythonVar是一个datetime.datetimestr(myPythonVar)作为"2013-10-30 05:04:09.797507",上述bash脚本将获得3级位置的变量,前两个与价值观2013-10-3005:04:09.797507.它的输出将是:

This bash script knows about 2013-10-30 and 05:04:09.797507
Run Code Online (Sandbox Code Playgroud)

如果你想命名变量并且你正在运行linux,这是一种方法:

%%script env my_bash_variable="$myPythonVariable" bash
echo myPythonVariable\'s value is $my_bash_variable
Run Code Online (Sandbox Code Playgroud)

您可以指定多个变量分配.再次提防引号和其他类似的事情(这里bash会痛苦地抱怨!).要了解其工作原理,请参见env手册页.


Ste*_*ell 41

要在bash命令中包含python变量,请使用!<some command>您可以使用的语法运行{<variable>},如下所示:

In [1]: for i in range(3):
   ...:     !echo {i+1}
   ...:     
1
2
3
Run Code Online (Sandbox Code Playgroud)

虽然这与OP提出的略有不同,但它与执行脚本任务密切相关且有用. 这篇文章有更多很棒的技巧和在IPython和Jupyter笔记本中使用shell命令的例子.

  • 链接断开。缓存在WIA中:https://web.archive.org/web/20160914042017/safaribooksonline.com/blog/2014/02/12/using-shell-commands-effectively-ipython/ (2认同)
  • 永远不会想到你可以如此随意地使用“!”。您甚至可以执行 `n = !echo {i + 1}`。 (2认同)

Vil*_*ira 9

如果像我这样的人最终在这里寻找如何在使用 运行命令时使用 Python 变量!,只需添加变量前缀$即可:

!echo $foobar
Run Code Online (Sandbox Code Playgroud)


小智 6

一个问题是,如果你想给你的 bash 的变量是一个列表,它不会按预期工作。

例如,在一个 python 单元格中:

l = ['A', 'B', 'C']
Run Code Online (Sandbox Code Playgroud)

然后,如果您将其直接提供给下一个单元格的魔术选项:

%%bash -s "$l"
for i in $1
do
echo $i
done
Run Code Online (Sandbox Code Playgroud)

它会像这样奇怪地分裂:

['A',
'B',
'C']
Run Code Online (Sandbox Code Playgroud)

最简单的答案是将代码放在大括号内{}以转换 bash 列表中的 python 列表,如下所示:

%%bash -s "{" ".join(l)}"
for i in $1
do
echo $i
done
Run Code Online (Sandbox Code Playgroud)

这给出了预期的输出:

A
B
C
Run Code Online (Sandbox Code Playgroud)


Dav*_*man 5

只是要注意一个变化,如果您需要将简单变量以外的其他内容传递给 bash 脚本:

%%bash -s $dict['key1'] $dict['key2'] $dict['key3']
Run Code Online (Sandbox Code Playgroud)

出了严重的错误,但是

%%bash -s {dict['key1']} {dict['key2']} {dict['key3']}
Run Code Online (Sandbox Code Playgroud)

效果很好。


kra*_*ski 5

如果您愿意使用以下方式定义新的魔法,则可以使用 Python 字符串模板:

from IPython import get_ipython
from IPython.core.magic import register_cell_magic

ipython = get_ipython()


@register_cell_magic
def pybash(line, cell):
    ipython.run_cell_magic('bash', '', cell.format(**globals()))
Run Code Online (Sandbox Code Playgroud)

然后如果你在 Python 中定义一个变量,如下所示:

test = 'Python variables'
Run Code Online (Sandbox Code Playgroud)

你可以使用它:

%%pybash
echo '{test} will be expanded'
echo '{{double braces will be replaced with single braces}}'
Run Code Online (Sandbox Code Playgroud)

导致:

Python variables will be expanded
{double braces will be replaced with single braces}
Run Code Online (Sandbox Code Playgroud)