在Java中,我们可以看到os.name
的属性值,以了解底层操作系统的名称:System.getProperty("os.name")
。
对于每个版本的Windows,它总是返回操作系统的确切名称:XP的Windows XP
,Vista的Windows Vista
,Seven的Windows 7
,8.1的Windows 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副本这个问题是否仍然存在 - 也就是说,这个错误是由Microsoft自动更新程序引起的?
这是已知问题JDK-8066504,已在即将发布的Java 8更新60中得到修复。
原因是GetVersionEx函数改变了自Windows 8.1以来的行为。
有多种可能的解决方法,请参阅MSDN article。
琐碎的一个是执行cmd.exe /c ver
。
另一种是查看其中一个系统文件的版本信息,例如kernel32.dll
。
这绝对是一个已知的错误。之所以会发生这种情况,是因为os.name
属性从Windows API源代码中的GetVersionEx
获取其值。然而,GetVersionEx
,
Windows 8.1之后可能会更改或不可用于发布
根据微软的官方网站。相反,我们需要使用IsWindows10OrGreater
文件中的Version Helper API函数中的versionhelpers.h
。正如您可能猜到的那样,此文件不是Java文件,而是用C语言编写的。因此,我们需要以稍微迂回的方式包含它。它需要相当多的工作(你需要在JNI中编程:/)但是this tutorial会帮助你做到这一点。另一个解决方案显示在this bug log中,并且确实需要更少的努力。
我遇到了同样的问题,使用了以下解决方法:cmd命令“systeminfo”返回“操作系统名称:”,这是操作系统的正确名称,为此编写了以下函数:
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;
}
嗯......我不知道它是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,而不是操作系统。)
您也可以使用.contains()
方法,只需检查“窗口”字符串可能沿着线
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来移动bug。
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
}
现在解释这里发生了什么:
System.getProperty("os.name")
将os的名称作为字符串返回.toLowerCase()
方法使返回的String小写.contains(String)
方法检查给定的输入字符串是否包含在被调用的String中