Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/file/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
从Java获取具有毫秒分辨率的文件mtime_Java_File_Last Modified - Fatal编程技术网

从Java获取具有毫秒分辨率的文件mtime

从Java获取具有毫秒分辨率的文件mtime,java,file,last-modified,Java,File,Last Modified,当我使用Files.getLastModifiedTime从Java读取文件的mtime时,返回值被截断为整秒。我知道这可以在其他系统上获得毫秒分辨率的MTIME,那么我的有什么不同呢 以下是编译并运行的完整独立测试: import java.nio.file.attribute.FileTime; import java.nio.file.Files; import java.nio.file.Paths; public class Test { public static void ma

当我使用
Files.getLastModifiedTime
从Java读取文件的
mtime
时,返回值被截断为整秒。我知道这可以在其他系统上获得毫秒分辨率的MTIME,那么我的有什么不同呢

以下是编译并运行的完整独立测试:

import java.nio.file.attribute.FileTime;
import java.nio.file.Files;
import java.nio.file.Paths;
public class Test {
  public static void main(String[] args) throws java.io.IOException {
    FileTime timestamp = Files.getLastModifiedTime(Paths.get("/tmp/test"));
    System.out.println(timestamp.toMillis());
  }
}
输出是(与我的特定测试文件一起)
1405602038000
,而
ls
显示:

$ ls --full-time /tmp/test                                                                                                                                                                                                    
-rw-rw-r-- 1 daniel daniel 0 2014-07-17 16:00:38.413008992 +0300 /tmp/test
我希望Java输出是
1405602038413


我在Linux上运行ext4。我尝试了openjdk 1.7和Oracle jdk 1.8。

您可以使用简单的日期格式来显示时间为毫秒:

java.nio.file.attribute.FileTime time = java.nio.file.Files.getLastModifiedTime(java.nio.file.Paths.get("/tmp/test"))
java.text.SimpleDateFormat dateformat = new java.text.SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS");
System.out.println(dateformat.format(time.toMillis()));

可以使用简单的日期格式显示时间为毫秒:

java.nio.file.attribute.FileTime time = java.nio.file.Files.getLastModifiedTime(java.nio.file.Paths.get("/tmp/test"))
java.text.SimpleDateFormat dateformat = new java.text.SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS");
System.out.println(dateformat.format(time.toMillis()));

我查看了源代码:

在Java 7的情况下,该方法以1秒的精度给出最后修改的时间戳:

在Java 8中,它看起来应该提供微秒精度:


但在这两种情况下,代码似乎都没有提供一种以不同精度获取时间戳的方法。

我查看了源代码:

在Java 7的情况下,该方法以1秒的精度给出最后修改的时间戳:

在Java 8中,它看起来应该提供微秒精度:


但是在这两种情况下,代码似乎都没有提供以不同精度获取时间戳的方法。

在Java 8中添加了以更高精度获取*nix系统上的文件时间戳的功能,但是,在本机端,它需要符合POSIX 2008的要求:

#if (_POSIX_C_SOURCE >= 200809L) || defined(__solaris__)
    (*env)->SetLongField(env, attrs, attrs_st_atime_nsec, (jlong)buf->st_atim.tv_nsec);
    (*env)->SetLongField(env, attrs, attrs_st_mtime_nsec, (jlong)buf->st_mtim.tv_nsec);
    (*env)->SetLongField(env, attrs, attrs_st_ctime_nsec, (jlong)buf->st_ctim.tv_nsec);
#endif

显然,您正在使用的Java构建没有设置它,因此时间戳的纳秒部分不可用,并且保持为零。

在Java 8中添加了在*nix系统上以更高精度获取文件时间戳的功能,但是,在本机端,它需要符合POSIX 2008的要求:

#if (_POSIX_C_SOURCE >= 200809L) || defined(__solaris__)
    (*env)->SetLongField(env, attrs, attrs_st_atime_nsec, (jlong)buf->st_atim.tv_nsec);
    (*env)->SetLongField(env, attrs, attrs_st_mtime_nsec, (jlong)buf->st_mtim.tv_nsec);
    (*env)->SetLongField(env, attrs, attrs_st_ctime_nsec, (jlong)buf->st_ctim.tv_nsec);
#endif

显然,您正在使用的Java构建没有设置它,因此时间戳的纳秒部分不可用并保持为零。

在Java 9中似乎是固定的

  • Oracle jdk 9.0.4-
    文件。getLastModifiedTime
    提供毫秒分辨率
  • Oracle jdk 1.8.162-
    文件。getLastModifiedTime
    提供第二种解决方案

它似乎在java 9中得到了修复

  • Oracle jdk 9.0.4-
    文件。getLastModifiedTime
    提供毫秒分辨率
  • Oracle jdk 1.8.162-
    文件。getLastModifiedTime
    提供第二种解决方案


你误解了。
time.toMillis
返回的值已被截断为整秒分辨率(即始终以三个零结尾)。这就是问题所在。这似乎很奇怪,因为当我在我的计算机上尝试它时,我得到了毫秒分辨率。我知道它对其他人有效(我编辑了这个问题以澄清这一点),但它在这里不起作用,我正试图找出原因。你误解了。
time.toMillis
返回的值已被截断为整秒分辨率(即始终以三个零结尾)。这就是问题所在。这似乎很奇怪,因为当我在我的计算机上尝试它时,我确实获得了毫秒分辨率。我知道它对其他人有效(我编辑了这个问题以澄清这一点),但它在这里不起作用,我正试图找出原因。似乎有关联。我能够在Ubuntu上重现Oracle Java 8的问题。当我使用调试器查看
UnixFileAttributes.st_mtime
时,它已经在几秒钟内完成了。本土方面有些问题。而且,即使在Java8(oracle构建,而不是openjdk)中使用,我也无法获得millis。当你运行Java8时,你真的能得到毫秒吗?@izstas宾果!我也在ubuntu上。现在我们只需要知道为什么Ubuntu版本(以及Oracle版本!)没有设置POSIX2008的兼容性。其他OSs或发行版的版本设置了它吗?这些代码是为哪些人运行的?如果你把这个变成一个答案,我会接受的,谢谢!目前的UbuntuJDK8确实提供了微秒级的精度。但是他们可以将其精确到纳秒级,因为评论中的那一刻“如果FileTime被更新为定义from(secs,nsecs)方法,我们可以重新访问它。”。从1.8开始,FileTime定义了一个from(Instant)方法。但除非文件系统以高精度存储时间戳,否则这一切都没有意义。我看到的消息来源说,时间戳精度在不同的文件系统中是高度可变的。(然后考虑时钟精度)似乎是相关的。我能够在Ubuntu上重现Oracle Java 8的问题。当我使用调试器查看
UnixFileAttributes.st_mtime
时,它已经在几秒钟内完成了。本土方面有些问题。而且,即使在Java8(oracle构建,而不是openjdk)中使用,我也无法获得millis。当你运行Java8时,你真的能得到毫秒吗?@izstas宾果!我也在ubuntu上。现在我们只需要知道为什么Ubuntu版本(以及Oracle版本!)没有设置POSIX2008的兼容性。其他OSs或发行版的版本设置了它吗?这些代码是为哪些人运行的?如果你把这个变成一个答案,我会接受的,谢谢!目前的UbuntuJDK8确实提供了微秒级的精度。但是他们可以将其精确到纳秒级,因为评论中的那一刻“如果FileTime被更新为定义from(secs,nsecs)方法,我们可以重新访问它。”。从1.8开始,FileTime定义了一个from(Instant)方法。但除非文件系统以高精度存储时间戳,否则这一切都没有意义。我看到的消息来源说,时间戳精度在不同的文件系统中是高度可变的。如果有人感兴趣的话,这个bug就在这里注册:如果有人感兴趣的话,这个bug在这里注册:也固定在Debian的1.80y229中,也固定在Debian的1.80y229中。