Windows 10下Java的"os.name"是什么?

55
在Java中,我们可以查看os.name属性的值来知道底层操作系统的名称:System.getProperty("os.name")
对于Windows的每个版本,它以前总是返回准确的操作系统名称:Windows XP用于XP,Windows Vista用于Vista,Windows 7用于Seven,Windows 8.1用于8.1等等...
问题是:我刚刚使用发布的Microsoft更新程序将我的Windows 8.1更新到了Windows 10,但这个属性似乎仍然保持为Windows 8.1
public class OSTest {
  public static void main(String[] args) {
    System.out.println(System.getProperty("os.name"));
  }
}

我该如何为此创建解决方法?还有,是否有人知道如果安装全新的Windows 10副本是否仍会出现此问题 - 即,这个bug是由微软自动更新程序引起的吗?


1
你正在运行哪个Java版本(我并不知道如何修复这个问题,除了等待Java或Windows的升级/修复)? - Hovercraft Full Of Eels
1
你重启了吗?在命令行上执行 ver 命令的结果是什么? - Elliott Frisch
4
为了升级操作系统,他必须完全重新启动。 - Hovercraft Full Of Eels
1
@HovercraftFullOfEels 为了完成Windows升级?当然。你确定他已经这样做了吗?我们中有些人不是魔法师Tim。 - Elliott Frisch
1
从冷启动验证,Java 1.8,Windows 10。Windows ver命令输出“Microsoft Windows [Version 10.0.10240]”- 因此我猜“a”解决方法是从Java内部调用ver命令。 - MadProgrammer
显示剩余4条评论
5个回答

50

这是一个已知的问题JDK-8066504,已在即将发布的Java 8更新60中修复。

原因是自Windows 8.1以来GetVersionEx函数已更改其行为。

有多种可能的解决方法,请参见MSDN文章

其中一个简单的方法是使用cmd.exe /c ver 命令。

另一个方法是查看其中一个系统文件(例如kernel32.dll)的版本信息。


17

这肯定是一个已知的 bug。它发生是因为 os.name 属性从 Windows API 的源代码中的 GetVersionEx 获取其值。但是,根据微软官方网站所述,GetVersionEx 可能会在 Windows 8.1 之后的版本中被更改或不可用。因此我们需要使用版本辅助 API 函数中的 IsWindows10OrGreater,该函数位于 versionhelpers.h 文件中。然而,这个文件不是 Java 文件,而是用 C 写成的。因此,我们需要以一种比较迂回的方式将其包含进来。虽然需要编写 JNI 代码,但 这个教程 将帮助您完成操作。还有一个解决方案显示在 这个 bug 记录 中,需要的工作量较少。


2
我遇到了同样的问题,使用了以下解决方法: cmd命令"systeminfo"返回"OS Name:",这是操作系统的正确名称,为此编写了以下函数:

我遇到了同样的问题,使用了以下解决方法:cmd命令"systeminfo"返回"OS Name:",这是操作系统的正确名称,为此编写了以下函数:

private boolean os2k10Check()
{
try{

    Process p = Runtime.getRuntime().exec("systeminfo");        /*Execute cmd command "systeminfo"*/
    BufferedReader r = new BufferedReader(new InputStreamReader(p.getInputStream()));
    String line;
    while (true) 
    {
        line = r.readLine();
        if (line == null) { break; }
        if(line.contains("OS Name:"))               /*If output contains OS Name and 2010*/
        {
        if(line.contains("2010"))
                return true;
        else
                return false;       
        }
    }
}
catch(Exception e)
    {System.out.println("Platform Type: os2010check: exception"+e);}

return false;
}

1

嗯...我不知道这是Windows 10 (10.0.17134.590)或Java 8 (1.8.0_171-b11 对于我来说)的修复,但现在它是正确的:os.name 给了我 Windows 10

此外,如果你不信任它,你可以检查 os.version。我有 10.0

(顺便说一下,我看到 os.arch:amd64。这是JVM的,不是操作系统的。)


-23
你也可以使用.contains()方法,只需检查"windows"字符串即可,可能是这样的。
if (System.getProperty("os.name").toLowerCase().contains("windows") && System.getProperty("os.name").toLowerCase().contains(windows version here [xp, 7, 8, etc]))){}

如果您需要 Windows 版本,可以检查所有版本,然后假定为 8.1 或 10 来解决该问题。
if (System.getProperty("os.name").toLowerCase().contains("windows") && System.getProperty("os.name").toLowerCase().contains("xp")){
//code for windows xp }

else if (System.getProperty("os.name").toLowerCase().contains("windows") && System.getProperty("os.name").toLowerCase().contains("vista")){
//code for windows vista

else if (System.getProperty("os.name").toLowerCase().contains("windows") && System.getProperty("os.name").toLowerCase().contains("7")){
//code for windows 7}

else if (System.getProperty("os.name").toLowerCase().contains("windows") && System.getProperty("os.name").toLowerCase().contains("8")){
//code for windows 8}
else if (System.getProperty("os.name").toLowerCase().contains("windows") && System.getProperty("os.name").toLowerCase().contains("8.1")){
//code for both windows 8.1 and 10

}

现在来解释这里发生了什么:
  1. if语句只是一个条件,用于确定Windows的版本。
  2. System.getProperty("os.name")返回操作系统的名称作为字符串。
  3. .toLowerCase()方法将返回的字符串转换为小写。
  4. .contains(String)方法检查所给定的输入字符串是否包含在被调用的字符串中。
  5. 最后一条语句允许除8.1和10之外的每个操作系统都使用不同的代码,它们需要作为一个块处理 :(

11
最后一句话允许为每个操作系统编写不同的代码,但不包括8.1和10。这正是问问题者不想要的。因此,这个答案实际上做了除回答问题以外的所有事情。 - user4157653

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接