搜索
bottom↓
回复: 14

这段C语言程序应该怎么改?

[复制链接]

出390入22汤圆

发表于 2017-10-22 15:19:45 | 显示全部楼层 |阅读模式
程序很简单,如下文,当cc=44时,lll=1520,不知应如何改
cs()
{
#define   yh 1524
unsigned long lll;
unsigned char cc;
for(cc=0;cc<200;cc++)
   {
    lll=yh*cc;
        NOP();
   }
}

阿莫论坛20周年了!感谢大家的支持与爱护!!

你熬了10碗粥,别人一桶水倒进去,淘走90碗,剩下10碗给你,你看似没亏,其实你那10碗已经没有之前的裹腹了,人家的一桶水换90碗,继续卖。说白了,通货膨胀就是,你的钱是挣来的,他的钱是印来的,掺和在一起,你的钱就贬值了。

出200入2554汤圆

发表于 2017-10-22 15:42:03 | 显示全部楼层
乘法溢出,改为: lll= yh*(unsigned long)cc ;

出20入70汤圆

发表于 2017-10-22 16:03:49 | 显示全部楼层
加个NOP()什么鬼,怕MCU累着了?

出20入30汤圆

发表于 2017-10-22 16:24:07 | 显示全部楼层
本帖最后由 HXDZ-AAA 于 2017-10-23 08:14 编辑

cs()
{
#define   yh 1524
unsigned int lll;
unsigned char cc;
for(cc=0;cc<200;cc++)
   {
//    lll=yh*cc;
         if(cc==44)
            lll=yh*cc;
   }
}

把lll改为unsigned int  Keil4编译通过,结果1520,就是利用16位无符模计算溢出。

出0入0汤圆

发表于 2017-10-22 17:19:15 | 显示全部楼层
计算过程中,右值溢出了?

出0入0汤圆

发表于 2017-10-22 17:44:46 | 显示全部楼层
lll=(unsigned long)yh*cc;

出0入0汤圆

发表于 2017-10-22 21:39:35 来自手机 | 显示全部楼层
结果溢出,先看看你的编译器long占几个字节吧

出0入0汤圆

发表于 2017-10-23 08:40:55 | 显示全部楼层
techbaby 发表于 2017-10-22 16:03
加个NOP()什么鬼,怕MCU累着了?

可能是基于这方面考虑。

出10入46汤圆

发表于 2017-10-23 08:59:57 | 显示全部楼层
没看懂楼主想要表达什么意思?

出0入8汤圆

发表于 2017-10-23 09:54:59 | 显示全部楼层
#define   yh 1524   改为 #define   yh 1524L

出390入22汤圆

 楼主| 发表于 2017-10-23 12:11:53 来自手机 | 显示全部楼层
照二楼改法,通过了,谢谢

出0入0汤圆

发表于 2017-10-31 23:09:02 来自手机 | 显示全部楼层
t3486784401 发表于 2017-10-22 15:42
乘法溢出,改为: lll= yh*(unsigned long)cc ;

这种类型转换,其实是为了扩展cc的长度,和yh对齐,不扩展不行吗?

出200入2554汤圆

发表于 2017-11-3 18:21:29 | 显示全部楼层
hnzbding 发表于 2017-10-31 23:09
这种类型转换,其实是为了扩展cc的长度,和yh对齐,不扩展不行吗?

不扩展不行。

按着原程序的意思,yh 是 16bit(某些编译器32位),cc 是 8bit,
乘法这一步输出结果某些编译器是 16bit,某些编译器负责一点给你 32bit,
这一步按照 C 的语法是先于赋值的,所以一旦被编译器卡到了 16bit,你赋值也只是 16bit 赋值。

一旦扩展了两个乘数的某一个是 32bit,C的语法就强制了输出结果不少于 32bit,这样也就通过了。
扩展写在后一个乘数上,是为了避免歧义:

  1. a*(unsigned long)b;        // 结果32bit有效
  2. (unsigned long)a*b;        // 结果32bit有效, 容易歧义
  3. (unsigned long)(a*b);        // 结果16bit有效
复制代码

出200入2554汤圆

发表于 2017-11-3 18:28:59 | 显示全部楼层
hnzbding 发表于 2017-10-31 23:09
这种类型转换,其实是为了扩展cc的长度,和yh对齐,不扩展不行吗?

以下这两个运算宏(内联函数)完成 32bit*32bit => 64bit 运算,摘自 VS2005 的 winnt.h
来自微软的谜之运算:

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x

出0入0汤圆

发表于 2017-11-28 15:40:14 | 显示全部楼层
t3486784401 发表于 2017-11-3 18:21
不扩展不行。

按着原程序的意思,yh 是 16bit(某些编译器32位),cc 是 8bit,

谢谢,看懂了一些,但还有疑惑。还拿1楼的代码做例子。

程序很简单,如下文,当cc=44时,lll=1520,不知应如何改
cs()
{
#define   yh 1524
unsigned long lll;
unsigned char cc;
for(cc=0;cc<200;cc++)
   {
    lll=yh*cc;
        NOP();
   }
}


你的意思是如果不扩展cc,编译器可能把yh按照8bit来处理,这样yh*cc的积就是16bit了;如果扩展了cc,就不会存在歧义,两个16bit的乘积是32bit。
但我有点疑惑,就是不管乘积是16bit还是32bit,lll不是都能存储得下吗,怎么编译会通不过?
回帖提示: 反政府言论将被立即封锁ID 在按“提交”前,请自问一下:我这样表达会给举报吗,会给自己惹麻烦吗? 另外:尽量不要使用Mark、顶等没有意义的回复。不得大量使用大字体和彩色字。【本论坛不允许直接上传手机拍摄图片,浪费大家下载带宽和论坛服务器空间,请压缩后(图片小于1兆)才上传。压缩方法可以在微信里面发给自己(不要勾选“原图),然后下载,就能得到压缩后的图片。注意:要连续压缩2次才能满足要求!!】。另外,手机版只能上传图片,要上传附件需要切换到电脑版(不需要使用电脑,手机上切换到电脑版就行,页面底部)。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|amobbs.com 阿莫电子技术论坛 ( 粤ICP备2022115958号, 版权所有:东莞阿莫电子贸易商行 创办于2004年 (公安交互式论坛备案:44190002001997 ) )

GMT+8, 2024-10-2 20:14

© Since 2004 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

快速回复 返回顶部 返回列表