C 中的 ISO 8601 周数
ISO 8601 week number in C
我正在尝试使用 C 获取 ISO8601 周数。我的 PC 上安装了 MinGW。 GCC 版本是 5.3.0。你可以在下面看到我的代码。 strftime 不适用于说明符“%V”。但它适用于说明符“%W”。但这不是我想要的。我需要 ISO 8601 格式的年份周数。
我已经用 2 个不同的在线 C 编译器尝试了我的代码,它们都运行良好。我怀疑我电脑上的编译器没有配置好。谁能告诉我我做错了什么?任何帮助将不胜感激。
这是我的代码:
#include <stdio.h>
#include <time.h>
#include <string.h>
int main ()
{
time_t timep;
struct tm * time_inf;
char buff [80];
time ( &timep );
time_inf = localtime ( &timep );
time_inf->tm_year = 2008 - 1900;
time_inf->tm_mon = 11;
time_inf->tm_mday = 31;
mktime ( time_inf );
strftime (buff, sizeof(buff), "%V", time_inf) ;
puts (buff); //prints nothing
printf("%d", strlen(buff)); //prints 0
return 0;
}
MinGW 不提供自己的 strftime
,但在 MSVCRT 的定义中提供链接,which doesn't provide %V
。
要么实现你自己缺少的东西,要么使用替代实现,例如 here's BSD's strftime.
to get the ISO8601 week number with C
当"%V"
和strftime()
不可用或有问题时,代码可以定向计算ISO 8601周。
ISO 8601 一年中的几周 从星期一开始。
当一个人想要找到年份的ISO 8601 week时,通常也需要相应的"year"。
一年中的第一周,即第 1 周,是从星期一开始的第一周,在 1 月至少有 4 天 - 或者如以下代码所用,一年中的第一个星期四在第 1 周.
有没有可能12月31日在下一年的第1周
1 月 1 日有可能在上一年的第 52/53 周。
#include <time.h>
// return 1 on failure, 0 on success
int tm_YearWeek(const struct tm *tmptr, int *year, int *week) {
// work with local copy
struct tm tm = *tmptr;
// fully populate the yday and wday fields.
if (mktime(&tm) == -1) {
return 1;
}
// Find day-of-the-week: 0 to 6.
// Week starts on Monday per ISO 8601
// 0 <= DayOfTheWeek <= 6, Monday, Tuesday ... Sunday
int DayOfTheWeek = (tm.tm_wday + (7 - 1)) % 7;
// Offset the month day to the Monday of the week.
tm.tm_mday -= DayOfTheWeek;
// Offset the month day to the mid-week (Thursday) of the week, 3 days later.
tm.tm_mday += 3;
// Re-evaluate tm_year and tm_yday (local time)
if (mktime(&tm) == -1) {
return 1;
}
*year = tm.tm_year + 1900;
// Convert yday to week of the year, stating with 1.
*week = tm.tm_yday / 7 + 1;
return 0;
}
例子
int main() {
struct tm tm = { 0 };
tm.tm_year = 2008 - 1900;
tm.tm_mon = 12 - 1;
tm.tm_mday = 31;
tm.tm_isdst = -1;
int y = 0, w = 0;
int err = tm_YearWeek(&tm, &y, &w);
printf("Err:%d Year:%d Week:%d %02d%02d\n", err, y, w, y%100, w);
return 0;
}
2008 年 12 月 31 日的输出是 2009 年第 1 周或 0901。根据上面的讨论,这是预期的,并且可以解释 OP 对 OP 代码的未声明关注。
Err:0 Year:2009 Week:1 0901
我正在尝试使用 C 获取 ISO8601 周数。我的 PC 上安装了 MinGW。 GCC 版本是 5.3.0。你可以在下面看到我的代码。 strftime 不适用于说明符“%V”。但它适用于说明符“%W”。但这不是我想要的。我需要 ISO 8601 格式的年份周数。
我已经用 2 个不同的在线 C 编译器尝试了我的代码,它们都运行良好。我怀疑我电脑上的编译器没有配置好。谁能告诉我我做错了什么?任何帮助将不胜感激。
这是我的代码:
#include <stdio.h>
#include <time.h>
#include <string.h>
int main ()
{
time_t timep;
struct tm * time_inf;
char buff [80];
time ( &timep );
time_inf = localtime ( &timep );
time_inf->tm_year = 2008 - 1900;
time_inf->tm_mon = 11;
time_inf->tm_mday = 31;
mktime ( time_inf );
strftime (buff, sizeof(buff), "%V", time_inf) ;
puts (buff); //prints nothing
printf("%d", strlen(buff)); //prints 0
return 0;
}
MinGW 不提供自己的 strftime
,但在 MSVCRT 的定义中提供链接,which doesn't provide %V
。
要么实现你自己缺少的东西,要么使用替代实现,例如 here's BSD's strftime.
to get the ISO8601 week number with C
当"%V"
和strftime()
不可用或有问题时,代码可以定向计算ISO 8601周。
ISO 8601 一年中的几周 从星期一开始。
当一个人想要找到年份的ISO 8601 week时,通常也需要相应的"year"。
一年中的第一周,即第 1 周,是从星期一开始的第一周,在 1 月至少有 4 天 - 或者如以下代码所用,一年中的第一个星期四在第 1 周.
有没有可能12月31日在下一年的第1周
1 月 1 日有可能在上一年的第 52/53 周。
#include <time.h>
// return 1 on failure, 0 on success
int tm_YearWeek(const struct tm *tmptr, int *year, int *week) {
// work with local copy
struct tm tm = *tmptr;
// fully populate the yday and wday fields.
if (mktime(&tm) == -1) {
return 1;
}
// Find day-of-the-week: 0 to 6.
// Week starts on Monday per ISO 8601
// 0 <= DayOfTheWeek <= 6, Monday, Tuesday ... Sunday
int DayOfTheWeek = (tm.tm_wday + (7 - 1)) % 7;
// Offset the month day to the Monday of the week.
tm.tm_mday -= DayOfTheWeek;
// Offset the month day to the mid-week (Thursday) of the week, 3 days later.
tm.tm_mday += 3;
// Re-evaluate tm_year and tm_yday (local time)
if (mktime(&tm) == -1) {
return 1;
}
*year = tm.tm_year + 1900;
// Convert yday to week of the year, stating with 1.
*week = tm.tm_yday / 7 + 1;
return 0;
}
例子
int main() {
struct tm tm = { 0 };
tm.tm_year = 2008 - 1900;
tm.tm_mon = 12 - 1;
tm.tm_mday = 31;
tm.tm_isdst = -1;
int y = 0, w = 0;
int err = tm_YearWeek(&tm, &y, &w);
printf("Err:%d Year:%d Week:%d %02d%02d\n", err, y, w, y%100, w);
return 0;
}
2008 年 12 月 31 日的输出是 2009 年第 1 周或 0901。根据上面的讨论,这是预期的,并且可以解释 OP 对 OP 代码的未声明关注。
Err:0 Year:2009 Week:1 0901