C 负时间转换提供随机值

C 负时间转换提供随机值,c,time,initialization,undefined-behavior,integer-overflow,C,Time,Initialization,Undefined Behavior,Integer Overflow,我试图计算C中两个时间点之间的差值,因为这些时间点在1900年之前,我需要使用负值 虽然转换应该将变量jahr_tod_negative写入ts.tm_year,但几乎每次我运行该程序时,它都会给我一个完全不同的日期,甚至是日期和月份都混在一起。年份是唯一需要为负值的值。我怎样才能防止呢 #include <stdio.h> #include <time.h> int main () { time_t t; struct tm ts; char

我试图计算C中两个时间点之间的差值,因为这些时间点在1900年之前,我需要使用负值

虽然转换应该将变量
jahr_tod_negative
写入
ts.tm_year
,但几乎每次我运行该程序时,它都会给我一个完全不同的日期,甚至是日期和月份都混在一起。年份是唯一需要为负值的值。我怎样才能防止呢

#include <stdio.h>
#include <time.h>

int main ()
{

    time_t t;
    struct tm ts;
    char str[90];

    int tag_tod;
    int monat_tod;
    int jahr_tod;
    unsigned int jahr_tod_von_1900;
    int jahr_tod_negative;


    printf("Tag eingeben: ");
    scanf("%d", &tag_tod);
    printf("\nMonat eingeben: ");
    scanf("%d", &monat_tod);
    printf("\nJahr eingeben: ");
    scanf("%d", &jahr_tod);
    jahr_tod_von_1900 = 1900 - jahr_tod;
    jahr_tod_negative = -jahr_tod_von_1900;
    printf("jahr_tod_negative: %d\n", jahr_tod_negative);


    //ts.tm_sec     = 0;
    //ts.tm_min     = 0;
    //ts.tm_hour  = 0;
    ts.tm_mday  = tag_tod;
    ts.tm_mon   = monat_tod;
    ts.tm_year  = jahr_tod_negative;     /* Jahr - 1900 */
    //ts.tm_wday  = 0;
    //ts.tm_yday  = 0;
    //ts.tm_isdst = 0;

    t = mktime(&ts);
    //printf("%s", asctime(&ts));
    printf("ts.tm_year: %d\n", ts.tm_year);
    strftime(str, 90, "%d. %B %Y", &ts);
    printf("Eingegebenes Datum: %s\n", str);

    return 0;
}
#包括
#包括
int main()
{
时间;
struct-tm-ts;
char-str[90];
int tag_tod;
国际货币基金组织;
内贾鲁托德;
未签名的int jahr_tod_von_1900;
int jahr_tod_阴性;
printf(“标签eingeben:”);
scanf(“%d”和标记_tod);
printf(“\n在eingeben:”);
scanf(“%d”和monat_tod);
printf(“\nJahr eingeben:”);
scanf(“%d”和jahr_tod);
jahr_tod_von_1900=1900-jahr_tod;
jahr_tod_negative=-jahr_tod_von_1900;
printf(“jahr_tod_负片:%d\n”,jahr_tod_负片);
//ts.tm_sec=0;
//ts.tm_min=0;
//ts.tm_小时=0;
ts.tm_mday=tag_tod;
ts.tm_mon=monat_tod;
ts.tm_year=jahr_tod_negative;/*jahr-1900*/
//ts.tm_wday=0;
//ts.tm_yday=0;
//ts.tm_isdst=0;
t=mktime(&ts);
//printf(“%s”,asctime(&ts));
printf(“ts.tm\U年:%d\n”,ts.tm\U年);
strftime(str,90,“%d.%B%Y,&ts);
printf(“eingegbenes数据:%s\n”,str);
返回0;
}
问题(可能还有其他问题)在于

jahr_tod_von_1900=1900-jahr_tod

您在此声明:

无符号整数jahr_tod_von_1900

如果
jahr_tod
实际大于
1900
,会发生什么情况?将负值隐式转换为无符号整数,通常会得到一个非常大的值

如果我扔掉所有的jahr_tod_消极的东西,只使用(一次!)

ts.tm_year=jahr_tod-1900


我总是能得到正确的答案。

对于初学者来说:你想正确初始化吗

struct tm ts;
在使用它之前。否则代码很可能会运行到未定义的行为中,因此任何事情都可能发生

至少


进一步假设

unsigned int jahr_tod_von_1900;
int jahr_tod_negative;
此声明

 jahr_tod_von_1900 = 1900 - jahr_tod;
jahr\u tod>1900
生成一个带符号的
整数环绕。后一种“溢出”也会导致未定义的行为。不要这样做

当您分配给一个
无符号的
时,要解决此问题,请确保执行“无符号”减法,例如:

jahr_tod_von_1900 = 1900U - (unsigned int) jahr_tod;

谁告诉你这应该管用的?我一点也不确定,但我担心它不能。@jdarthenay大约4/10次输出正确的值,其他6次似乎是随机的。这很有趣。能有机会对一个问题进行投票以改变现状是很好的:)你能给出你正在使用的信息吗?如果您正在构建32位或64位的程序,则同样精确。@jdarthenay尝试输入:例如1456(工作)、1568(随机数),大于1900的每个数字都输出正确的值。顺便说一句,它是64位的。大于1900的值给出正确的输出,因为正值被添加到1900。猜测答案通常没有帮助。有了这一点,答案往往是低质量的…:-(如果不确定,最好发表评论。@alk我尝试了我的解决方案:即使没有初始化,它也能在OS X上工作。因此溢出是一个问题。我不反对你写的关于“溢出”的内容,但反对你是如何写的(->“我想”)。如果不确定,不要回答。简单!;-)@alk,好的,我首先写了我的假设,然后我按原样编译了代码,并尝试了我的重写,然后给出了正确的结果。他真的不投,糟糕的术语。。。
jahr_tod_von_1900 = 1900U - (unsigned int) jahr_tod;