何时使用 os.name、 sys.Platform 或 platform.system?

据我所知,Python 有3种方法可以找出操作系统的运行情况:

  1. os.name
  2. sys.platform
  3. platform.system()

了解这些信息在条件导入或使用不同平台之间的功能(例如,Windows 上的 time.clock()和 UNIX 上的 time.time())中通常很有用。

我的问题是,为什么会有三种不同的方法呢?什么时候应该使用一种方法而不是另一种方法?哪种方式是“最好的”(最不可能或最不可能意外地排除一个特定的系统,您的程序实际上可以运行在这个系统上) ?

看起来 sys.platformos.name更具体,这样你就可以区分 win32cygwin(与 nt相对) ,以及 linux2darwin(与 posix相对)。但是如果是这样的话,那么 sys.platformplatform.system()之间的区别是什么呢?

例如,哪个更好,这个:

import sys
if sys.platform == 'linux2':
# Do Linux-specific stuff

还是这个:

import platform
if platform.system() == 'Linux':
# Do Linux-specific stuff

现在我将坚持 sys.platform,所以这个问题不是特别紧急,但我会非常感谢一些澄清关于这一点。

61136 次浏览

我相信平台模块可能是新代码的首选。其他人在它之前就存在了。这是一种进化,其他的则是为了向后兼容。

来自 sys.platform文件:

通常,测试某些功能是否可用的“最佳”未来防范方法就是尝试使用它,如果失败则使用备份。

那么 sys.Platform 和 platform.system ()之间的区别是什么呢?

platform.system() 返回一个标准化值,它可能从以下几个来源获得: os.uname()sys.platformver命令(在 Windows 上)。

深入研究了一下源代码。

sys.platformos.name的输出在编译时确定。 platform.system()在运行时确定系统类型。

  • sys.platform在生成配置期间指定为编译器定义。
  • os.name检查某些特定于 OS 的模块是否可用(例如 posixnt、 ...)
  • platform.system()实际上运行 uname和其他几个函数,以便在运行时确定系统类型。

我的建议是:

  • 使用 os.name检查它是否是一个依从 posx 的系统。
  • 使用 sys.platform检查它是否是一个 linux,cygwin,darwin,atheos 等。
  • 如果您不相信其他来源,请使用 platform.system()

platform.system()sys.platform之间有一条细线的差异,有趣的是大多数情况下 platform.system()退化为 sys.platform

下面是来源 Python2.7\Lib\Platform.py\system所说的

def system():


""" Returns the system/OS name, e.g. 'Linux', 'Windows' or 'Java'.


An empty string is returned if the value cannot be determined.


"""
return uname()[0]


def uname():
# Get some infos from the builtin os.uname API...
try:
system,node,release,version,machine = os.uname()
except AttributeError:
no_os_uname = 1


if no_os_uname or not filter(None, (system, node, release, version, machine)):
# Hmm, no there is either no uname or uname has returned
#'unknowns'... we'll have to poke around the system then.
if no_os_uname:
system = sys.platform
release = ''
version = ''
node = _node()
machine = ''

也是根据 文件

()

返回一个包含标识当前操作系统的信息的5个元组, 一些系统将节点名截断为8 字符或前导组件; 获取 Hostname 是 socket.gethostname ()或甚至 Gethostbyaddr (socket.gethostname ()).

Availability: recent flavors of Unix.

这取决于你是喜欢引发异常还是在未经测试的系统上尝试任何东西,以及你的代码是如此高级还是如此低级,以至于它可以或不能在类似的未经测试的系统上工作(例如,未经测试的 Mac-‘ posx’或嵌入式 ARM 系统)。更简单的方法是不枚举所有已知的系统,而是测试可能的相关属性。(例如,它被认为重要的是系统的优越性,而不是重要的多处理属性。)

  • Name 是正确使用 os模块的足够解析度。可能的值是 Python 2.7中的‘ posx’、‘ nt’、‘ os2’、‘ ce’、‘ java’或‘ riscos’,而自 Python 3.4以来只使用了‘ posx’、‘ nt’和‘ java’。

  • Sys.Platform 是一种更好的分辨率。建议使用 if sys.platform.startswith('linux')习惯用法,因为“ linux2”意味着 Linux 内核版本2。Xx 或者3。旧的内核目前从不使用。在 Python 3.3中,所有的 Linux 系统都是简单的“ Linux”。

我不知道“ Mac”和“ Java”系统的具体细节,所以我不能使用非常好的 platform.system ()方法的结果进行分支,但是我会使用 platform模块的优点进行消息和错误日志记录。