有两种回答方式。
第一个(短的)
要获得在 R 中执行语句或代码块的时间,您可以使用“system.time”。在规范中 - “返回 expr 使用的 CPU(和其他)时间。” - 它接近 C++ 中的clock(),因为标准中提到了时钟 - “返回程序消耗的处理器时间。”
所以,我的回答是:您可以比较 C++(使用时钟)和 R(使用 system.time())中的执行时间。
第二个(很长)
我打开了 R-3.3.1.tar.gz 文件并在文件夹 src 中为一些看起来与此问题相关的文件提供了资金。
在文件system.c(声明)中:
void R_setStartTime(void); /* in sys-unix.c */
在文件in sys-unix.c(定义)中:
void R_setStartTime(void)
{
#ifdef HAVE_SYSCONF
clk_tck = (double) sysconf(_SC_CLK_TCK);
#else
# ifndef CLK_TCK
/* this is in ticks/second, generally 60 on BSD style Unix, 100? on SysV
*/
# ifdef HZ
# define CLK_TCK HZ
# else
# define CLK_TCK 60
# endif
# endif /* not CLK_TCK */
clk_tck = (double) CLK_TCK;
#endif
/* printf("CLK_TCK = %d\n", CLK_TCK); */
StartTime = currentTime();
}
和
/* NOTE
This used to use times() for elapsed times, which is measured in
clock ticks (which can overflow). It is possible this version uses
time() and so is in seconds. But even Cygwin has gettimeofday.
*/
attribute_hidden
void R_getProcTime(double *data)
{
/* docs say this is rounded to the nearest ms */
double et = currentTime() - StartTime;
data[2] = 1e-3 * rint(1000*et);
#ifdef HAVE_GETRUSAGE
/* all known current OSes */
struct rusage self, children;
getrusage(RUSAGE_SELF, &self);
getrusage(RUSAGE_CHILDREN, &children);
data[0] = (double) self.ru_utime.tv_sec +
1e-3 * (self.ru_utime.tv_usec/1000);
data[1] = (double) self.ru_stime.tv_sec +
1e-3 * (self.ru_stime.tv_usec/1000);
data[3] = (double) children.ru_utime.tv_sec +
1e-3 * (children.ru_utime.tv_usec/1000);
data[4] = (double) children.ru_stime.tv_sec +
1e-3 * (children.ru_stime.tv_usec/1000);
#else
/* Not known to be currently used */
struct tms timeinfo;
times(&timeinfo);
data[0] = fround(timeinfo.tms_utime / clk_tck, 3);
data[1] = fround(timeinfo.tms_stime / clk_tck, 3);
data[3] = fround(timeinfo.tms_cutime / clk_tck, 3);
data[4] = fround(timeinfo.tms_cstime / clk_tck, 3);
#endif
}
而times.c中定义的currentTime()如下:
double currentTime(void)
{
double ans = NA_REAL;
#ifdef HAVE_TIMESPEC_GET
struct timespec tp;
int res = timespec_get(&tp, TIME_UTC);
if(res != 0)
ans = (double) tp.tv_sec + 1e-9 * (double) tp.tv_nsec;
#elif defined(HAVE_CLOCK_GETTIME) && defined(CLOCK_REALTIME)
/* Has 2038 issue if time_t: tv.tv_sec is 32-bit. */
struct timespec tp;
int res = clock_gettime(CLOCK_REALTIME, &tp);
if(res == 0)
ans = (double) tp.tv_sec + 1e-9 * (double) tp.tv_nsec;
#elif defined(HAVE_GETTIMEOFDAY)
/* Mac OS X, mingw.org, used on mingw-w64.
Has 2038 issue if time_t: tv.tv_sec is 32-bit.
*/
struct timeval tv;
int res = gettimeofday(&tv, NULL);
if(res == 0)
ans = (double) tv.tv_sec + 1e-6 * (double) tv.tv_usec;
#else
/* No known current OSes */
time_t res = time(NULL);
if(res != (time_t)(-1)) /* -1 must be an error as the real value -1
was ca 1969 */
ans = (double) res;
#endif
#ifndef HAVE_POSIX_LEAPSECONDS
/* No known current OSes */
/* Disallowed by POSIX (1988-):
http://www.mail-archive.com/leapsecs@rom.usno.navy.mil/msg00109.html
https://en.wikipedia.org/wiki/Unix_time
*/
if (!ISNAN(ans)) {
ans -= n_leapseconds;
}
#endif
return ans;
}
因此,我们可以看到 R 中时间检测的实现很大程度上取决于平台。比如times.c开头的cmets解释:
函数clock() 是C99 并在time.h 中定义。它测量CPU
CLOCKS_PER_SEC 的时间:存在整数的小危险
溢出。
函数 times() 是 POSIX 并在sys/times.h 中定义。它
以时钟滴答为单位返回经过的时间,加上以 a 为单位的 CPU 时间
struct tms* 参数(也在时钟节拍中)。
所以答案是:测量方法可能不同,但测量单位和测量值的定义方式相同,因此没关系,这是 clock() 按照 C99 或 times() 按照 POSIX -这是 CPU 时间。