注册 登录
编程论坛 C语言论坛

萌新初来乍到,请多指教

小冯A 发布于 2021-10-12 12:31, 1650 次点击
变量x,y为double类型,变量a,b为int类型,数学式6*a*b/(7*x*y)的表达式为什么是   6/x*a*b/7/y
3 回复
#2
自由而无用2021-10-12 13:46
//online parser: https://www.bccn.net/run/
程序代码:
#include <stdio.h>

int main(int argc, char *argv[])
{
    int a, b;
    //add volatile to mask gcc overdoing optimization
    volatile double x, y;
    double formula;

#define critical_section_in
    ((int *)&a)[0] = 10;
    ((int *)&a)[1] = 20;
    *(double *)&((int *)&a)[2] = 1.25;
    *(double *)&((int *)&a)[4] = 12.17;
#define critical_section_out

//attention: while closed print_on gcc optimized the statment (7.0 * x * y)
#define PRINT_ON
#ifdef PRINT_ON
    printf("a = %p\n", &a);
    printf("a = %d\n", a);
    printf("b = %d\n", b);
    printf("(a->x) = %p-----", &((int *)&a)[2]);
    printf("x = %p\n", &x);
    printf("x = %lf\n", x);
    printf("y = %lf\n", y);
#endif

    formula =  6 * a * b;
    formula = formula / (7.0 * x * y);
    printf("f = %.2lf\n", formula);

    return 0;
}


output sample:
a = 0x7ffee15347f8
a = 10
b = 20
(a->x) = 0x7ffee1534800-----x = 0x7ffee1534800
x = 1.250000
y = 12.170000
f = 11.27

[此贴子已经被作者于2021-10-12 13:53编辑过]

#3
rjsp2021-10-13 07:54
交代一下必要的上下文信息吧,没头没脑的你让人怎么回答?
比如我问你“俺隔壁村子的马二狗为什么半夜起床?”,你怎么答?撒尿、拉屎、梦游、打蚊子、去做贼、闻鸡起舞、……都有可能,而可能的种类无限多。

可能是作者处理的数据中,a*b 过大会溢出,而作者又不知道可以写成 6.0*a*b/(7*x*y);
也可能是作者处理的数据中,x更接近6,先计算 6/x 可以提高精度;
也可能是作者处理的数据中,6/x*a更接近1,先计算 6/x*a 可以提高精度;
也可能是……
也可能是其它人就是这么写的,因为浮点数不满足结合律,所以算式不同会导致结果不同。
也可能是……
#4
自由而无用2021-10-13 09:10
//online parser: https://www.bccn.net/run/?lang=c
程序代码:
#include <stdio.h>

int main(int argc, char *argv[])
{
    int a, b;
//#define MASK_GCC_OVERDOING
#ifdef MASK_GCC_OVERDOING
    //add volatile to mask gcc CT(compile-time) overdoing optimization
    /* runtime check */
    volatile double x, y;
#else
    /* compile-time check */
    double x, y;
#endif
    double formula;

#define runtime_block__IN
/* as gcc unable to check runtime code */
    ((int *)&a)[0] = 10;
    ((int *)&a)[1] = 20;
    *(double *)&((int *)&a)[2] = 1.25;
    *(double *)&((int *)&a)[4] = 12.17;
#define runtime_block__OUT

#ifdef MASK_GCC_OVERDOING
//attention: while closed print_on gcc optimized the expression (7.0 * x * y)
#define PRINT_ON
#ifdef PRINT_ON
    printf("a = %p\n", &a);
    printf("a = %d\n", a);
    printf("b = %d\n", b);
    printf("(a->x) = %p-----", &((int *)&a)[2]);
    /*while CT checking, until here gcc finally realized the exsitence of x, y*/
    printf("x = %p\n", &x);
    printf("x = %lf\n", x);
    printf("y = %lf\n", y);
#endif
#endif /*MASK_GCC_OVERDOING*/

    formula =  6 * a * b;
    /* CT: 7.0 * x * y = 0 so got the f = inf[divide zero] */
    formula = formula / (7.0 * x * y);
    printf("f = %.2lf\n", formula);

    return 0;
}


output sample:
f = inf
#5
diycai2021-10-13 11:21
回复 3楼 rjsp

让我想起了20年前的一个很火的网游MU,角色死亡惩罚是身上携带的金钱扣除30%。
程序员是这么处理的:
int money = xxx;//角色持有金钱数量
money = money - (moeny*3/10);
然后就被玩家发现了bug,大家争先恐后带着巨额金钱出城自杀。
#6
jianghushife2021-10-14 16:10
1