V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
推荐学习书目
Learn Python the Hard Way
Python Sites
PyPI - Python Package Index
http://diveintopython.org/toc/index.html
Pocoo
值得关注的项目
PyPy
Celery
Jinja2
Read the Docs
gevent
pyenv
virtualenv
Stackless Python
Beautiful Soup
结巴中文分词
Green Unicorn
Sentry
Shovel
Pyflakes
pytest
Python 编程
pep8 Checker
Styles
PEP 8
Google Python Style Guide
Code Style from The Hitchhiker's Guide
mainlong
V2EX  ›  Python

请教,`python3 abc.py` 和`./abc.py` 的运行机制不一样吗?

  •  
  •   mainlong · 2021-11-19 18:16:42 +08:00 · 2646 次点击
    这是一个创建于 859 天前的主题,其中的信息可能已经有所发展或是发生改变。

    在 Windows 写了一个 py 文件,上传到 Ubuntu 后。

    使用python3 abc.py运行,正常输出。

    使用./abc.py运行后报错,查询了下是 Windows 换行符的问题。编辑器设置 Unix 风格后两者输出正常。

    想请教下前者怎么没有发现换行符的问题?两者是怎么运行代码的?

    代码和执行结果

    10 条回复    2021-11-21 18:03:28 +08:00
    ysc3839
        1
    ysc3839  
       2021-11-19 18:27:07 +08:00   ❤️ 10
    不一样。
    ./abc.py 是用 Unix Shebang 特性把脚本当成可执行文件执行,内核会先判断文件是不是#!开头,如果是,就会执行第一行去掉开头#!后对应路径的程序。因为 Unix 使用 LF 换行符,此时第一行末尾包含了一个 CR 字符,于是就找不到对应的程序了。
    python3 abc.py 是直接用 Python 解释器执行,首先 Python 解释器是支持 CRLF 换行符的,其次第一行因为是#开头,会被忽略。
    gam2046
        2
    gam2046  
       2021-11-19 18:27:25 +08:00   ❤️ 1
    python 不熟悉,盲猜一手。

    ./adb.py ,先由 shell 进行解析,但由于 CRLF 的原因,#!/usr/bin/env python 这一行读出来多了 CR 。

    而 python3 abc.py 则直接调用了 python 解析脚本,对于这种 CRLF 有兼容处理。
    CokeMine
        3
    CokeMine  
       2021-11-19 18:27:54 +08:00 via Android   ❤️ 1
    你加了 Python 的 Shebang 所以直接执行这个脚本就默认调用了 Python 的解释器。
    但是如果你去掉 Shebang 或者不给这个脚本可执行权限。应该直接执行就跑不动了
    我觉得你出现这样结果的原因是因为 前者能运行是因为 Python 解释器对于两种换行符都能运行。但是因为换行符问题后者对 Linux 来说不是一个合法的脚本。自然也找不到对应的解释器去解释他
    ch2
        4
    ch2  
       2021-11-19 18:29:22 +08:00   ❤️ 2
    命令里声明用 python3 ,肯定没问题
    不指定用哪个解释器,shell 会去第一行读你钦定的 bin
    结果读到了一个叫 python3\r 的玩意
    shell 想请教你:它在 /usr/bin/env 里没找到 python3\r ,现在该干啥?
    第二次,你把\r 去掉后,shell 找到了 /usr/bin/env/python3 ,就让它去跑这个脚本了
    ysc3839
        5
    ysc3839  
       2021-11-19 19:07:41 +08:00   ❤️ 2
    @gam2046 @ch2
    Shebang 不是 shell 解析的,而是内核解析的。
    比如 Linux 是在 binfmt_script.c 里解析的:
    https://github.com/torvalds/linux/blob/v5.15/fs/binfmt_script.c
    aeron
        6
    aeron  
       2021-11-19 21:33:50 +08:00 via iPhone
    @ysc3839 学到了
    canwushuang
        7
    canwushuang  
       2021-11-20 09:52:13 +08:00
    linux 中,脚本文件第一行当作运行环境申明。shell bash python node 等等都如此。
    canwushuang
        8
    canwushuang  
       2021-11-20 09:55:31 +08:00
    windows 中,最早引入了文件扩展名,后缀名,此后根据不同后缀查询不同的环境设置并运行。
    windvans
        9
    windvans  
       2021-11-20 17:46:18 +08:00
    要看第一行#!后面指定的解释器啊
    shm7
        10
    shm7  
       2021-11-21 18:03:28 +08:00
    2 3 4 楼就是一眼能猜到的原因了,python 命令路径错误指定了,windows 和 linux 下路径不一样。
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   我们的愿景   ·   实用小工具   ·   5527 人在线   最高记录 6543   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 27ms · UTC 08:59 · PVG 16:59 · LAX 01:59 · JFK 04:59
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.