李迟2011年3月代码积累
上个月积累的代码如下,由于在同一文件中测试多个代码段,因此只好用#if 0 ……#endif的形式来控制了。这次的代码包括:
1、测试函数入栈顺序,入栈顺序依据语言的不同而不同,C语言是从右到左的。从代码的运行结果也可以看出,因为栈帧是往下增长的。
2、从字符串中去除指定字符,这里在csdn帖子中抄来的,原问题是说出现了段错误,因为他使用的不是字符数组。详见代码。
3、移位操作,从http://aggregate.ee.engr.uky.edu/MAGIC/抄来的,上面有许多位运算的技巧。那个大小端转换是我自己临时加上去的,因为以前雄心勃勃想研究SD卡时候曾经写过,一时心血来潮也写一下,没想到还没忘记。
4、计算一个数的二进制中包含1的个数,比如7的二进制为0111,则1的个数为3。最后结果和3f相与,一开始不太理解,后来想通了,因为32位的二进制中1的个数最多是32个(似乎是废话)。那个求msb(搞过单片机的应该很熟悉这个东西)的函数中,结果是这样的:比如0x64,二进制为0x0110 0100,最高有效位为0x0100 0000,则结果为0x40。本文所有代码片段可任意使用而不用告诉作者,当然,作者修改了也不必要告知阁下,而且,由于代码的错误而造成的损失亦与作者无关,不过一起讨论、学习还是可以的。
/*************************************************
没有main函数
$ gcc rock.c -Wall
/usr/lib/gcc/i386-redhat-linux/4.3.0/../../../crt1.o: In function `_start':
(.text+0x18): undefined reference to `main'
collect2: ld 返回 1
**************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#if 0
/**************************************************
* 参数入栈测试
编译过程中出现警告:
$ gcc rock.c -Wall
rock.c: 在函数‘main’中:
rock.c:55: 警告:‘t’上的运算结果可能是未定义的
rock.c:57: 警告:‘t’上的运算结果可能是未定义的
rock.c:61: 警告:‘j’上的运算结果可能是未定义的
rock.c:61: 警告:‘j’上的运算结果可能是未定义的
rock.c:51: 警告:未使用的变量‘i’
测试结果:
$ ./a.out
6 6
6 6
a=6[0xbfaeca30] b=7[0xbfaeca34] c=7[0xbfaeca38]
20
了解过堆栈帧的话,应该知道参数入栈的顺序
**************************************************/
int foo(int a, int b, int c)
{
printf("a=%d[%p] ",a, &a);
printf("b=%d[%p] ",b, &b);
printf("c=%d[%p]/n",c, &c);
return a+b+c;
}
int main(void)
{
int i = 3;
int j = 5;
int ret;
int t = 5;
printf("%d %d/n", ++t, t);
t = 5;
printf("%d %d/n", t, ++t);
//printf("%d %d %d/n", i++, ++i, i);
//printf("%d %d %d/n", j, ++j, j++);
//ret = foo(i++, ++i, i);
ret = foo(j++, ++j, j);
printf("%d/n", ret);
return 0;
}
/*xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
* 参数入栈测试 结束
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/
#endif
/*************************************************
* 字符串去除特定字符
* 段错误
运行结果:
$ ./a.out
Before: abcdabcdabcdefgabcd
After: abdabdabdefgabd
*************************************************/
#if 0
#include <string.h>
void SqueezeChar(char s[],int c)
{
int i,j;
for(i=j=0;i<strlen(s);i++)
if(s[i]!=c)
s[j++]=s[i]; s[j]='/0';
}
int main(void)
{
//char * org="abcdabcdabcdefgabcd"; // 此处造成段错误
char org[] = "abcdabcdabcdefgabcd";
printf("Before:/t%s/n",org);
SqueezeChar(org,'c');
printf("After:/t%s/n",org);
return 0;
}
/*xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
* 字符串去除特定字符 结束
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/
#endif
#if 0
/************************************************
8位、16位、32位平台无符号位反转,如0000ffff --> ffff0000
注:实际中需要注意位数需要一致。比如,不能将unsigned int版本的反转用于unsigned char中。
来自 http://aggregate.ee.engr.uky.edu/MAGIC/
运行结果:
$ ./a.out
fffe 7fff0000
7f fe00
fe 7f
55aa8977 7789aa55
55aa aa55
*************************************************/
#include <stdio.h>
/* fe --> 7f */
unsigned char reverse8(register unsigned char x)
{
x = (((x & 0xaa) >> 1) | ((x & 0x5555) << 1));
x = (((x & 0xcc) >> 2) | ((x & 0x3333) << 2));
return((x >> 4) | (x << 4));
}
/* 007f --> fe00 */
unsigned short reverse16(register unsigned short x)
{
x = (((x & 0xaaaa) >> 1) | ((x & 0x5555) << 1));
x = (((x & 0xcccc) >> 2) | ((x & 0x3333) << 2));
x = (((x & 0xf0f0) >> 4) | ((x & 0x0f0f) << 4));
return((x >> 8) | (x << 8));
}
/* fffe --> 7fff0000 */
unsigned int reverse32(register unsigned int x)
{
x = (((x & 0xaaaaaaaa) >> 1) | ((x & 0x55555555) << 1));
x = (((x & 0xcccccccc) >> 2) | ((x & 0x33333333) << 2));
x = (((x & 0xf0f0f0f0) >> 4) | ((x & 0x0f0f0f0f) << 4));
x = (((x & 0xff00ff00) >> 8) | ((x & 0x00ff00ff) << 8));
return((x >> 16) | (x << 16));
}
/* 大小端转换,如 55aa6788 --> 8867aa55 */
unsigned int endian_reverse32(register unsigned int x)
{
return ((x & 0xff) << 24) | ((x & 0xff00) << 8) | ((x & 0xff0000) >> 8) | ((x & 0xff000000) >> 24);
}
/* 大小端转换, 如55aa --> aa55 */
unsigned short endian_reverse16(register unsigned short x)
{
return ((x & 0xff) << 8) | ((x & 0xff00) >> 8);
}
int main(void)
{
unsigned int i = 65534;
unsigned int tmp = reverse32(i);
unsigned short j = 127;
unsigned short tmp1 = reverse16(j);
unsigned char k = 254;
unsigned char tmp2 = reverse8(k);
unsigned int tmp3 = 0x55aa8977;
unsigned int tmp4 = endian_reverse32(tmp3);
unsigned short tmp5 = 0x55aa;
unsigned short tmp6 = endian_reverse16(tmp5);
printf("%x %x/n", i, tmp);
printf("%x %x/n", j, tmp1);
printf("%x %x/n", k, tmp2);
printf("%x %x/n", tmp3, tmp4);
printf("%x %x/n", tmp5, tmp6);
return 0;
}
/*xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
* 位反转 结束
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/
#endif
#if 0
/*************************************************
计算二进制中1的个数
运行结果:
$ ./a.out
64 3 3 40
0x64 = 0110 0100 (共3个1)
0x40 = 0100 0000
*************************************************/
/* 计算一个数(32位无符号)的二进制中1的个数
* 以x = 999测试,34条指令,占4个字节栈空间
*/
unsigned int binary_count(unsigned int x)
{
unsigned int count = 0;
while (x)
{
count++;
//x = x&(x-1); /* 与 */
x &= x-1; /* 与 */
#ifdef DEBUG
printf("%x ", x); /* debug */
#endif
}
return count;
}
/* 另一个版本
* 以x = 999测试,30条指令,不占栈空间
* 最后一语句x & 0x0000003f, 因为32位1的个数最多只能是32位。
*/
unsigned int ones32(register unsigned int x)
{
/* 32-bit recursive reduction using SWAR...
but first step is mapping 2-bit values
into sum of 2 1-bit values in sneaky way
*/
x -= ((x >> 1) & 0x55555555);
x = (((x >> 2) & 0x33333333) + (x & 0x33333333));
x = (((x >> 4) + x) & 0x0f0f0f0f);
x += (x >> 8);
x += (x >> 16);
return(x & 0x0000003f);
}
/* 求一个数中的MSB */
unsigned int msb32(register unsigned int x)
{
x |= (x >> 1);
x |= (x >> 2);
x |= (x >> 4);
x |= (x >> 8);
x |= (x >> 16);
return(x & ~(x >> 1));
}
/* ?? */
unsigned int tzc(register int x)
{
return(ones32((x & -x) - 1));
}
int main(void)
{
unsigned int x = 100;
unsigned int y = ones32(x);
unsigned int tmp = binary_count(x);
unsigned int tmp1 = msb32(x);
printf("%x %x %x %x/n", x, y, tmp, tmp1);
return 0;
}
/*xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
* 二进制中1的个数 结束
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/
#endif
李迟2011年3月代码积累相关推荐
- 李迟2011年4月知识积累
我从来不觉得写代码只是写代码的事,也不是整天拿数据结构和算法来研究,拿C.C++大头书来看.我对自己的要求是:坚持融会贯通,坚持多层次联系,坚持学习,坚持积累. 非代码知识 主要关于linux日常使用 ...
- 李迟2021年12月知识总结
本文为 2021 年 12 月知识总结. 研发编码 测试发现,不同语言对浮点数的存储和处理不太相同,比如1.5,有的语言存储的可能是1.49999999999,有的可能是1.500000001.这样四 ...
- 李迟2021年11月知识总结
本文为 2021 年 11 月知识总结. 研发编码 C / C++ 无. golang 保留小数点后2位,假定在原数值基础上上浮10%(即1.1倍),但不进位. // 使用Sprintf有些情况会导致 ...
- 李迟2021年10月知识总结
本文为 2021 年 10 月知识总结. 研发编码 C / C++ 无. golang 写了数字签名.数字信封的测试示例,了解了 RSA .AES 加解密,知道 AES 的密钥长度必须大于16字节. ...
- 李迟2022年1月知识总结
本文为 2022 年 1 月知识总结. 研发编码 Golang golang中中文字符长度为3,如下示例中,判断某字段中文开头是否为"广西"二字,如是则舍去,只保留后面的字符串,如 ...
- 李迟2022年10月工作生活总结
本文为 2022 年 10 月工作生活总结. 研发编码 Go 判断interface{}是否为空 判断interface{}类型是否为空,不能直接使用==nil来判断(用之无效),需先用reflect ...
- 李迟2021年8月知识总结
本文为 2021 年 8 月知识总结. 编码总结 C / C++ 产生随机数示例二则. 产生给出范围,并指定数量的随机数.即给定数组(实为向量),其内可预先定义有数值,也可以为空,产生随机数时,需保留 ...
- 李迟2021年6月知识总结
本文为 2021 年 6 月知识总结. 编码总结 C / C++ 使用sscanf检查不确定的输入参数: char name[8] = {0};int type = 0;int threadnum = ...
- 李迟2022年8月工作生活总结
本文为 2022 年 8 月工作生活总结. 研发编码 Java 接手了一个 Java 工程事务(注:不是接手工程),在其中添加一个模块.不知为何领导会找到我,或者是没有负责项目的原故,作为十分珍惜工作 ...
最新文章
- (曲率系列2:)Paper6:Curvature Estimation of 3D Point Cloud Surfaces Through the Fitting of Normal
- Selenium提取数据之标签对象提取文本内容和属性值
- oracle创建定时任务
- Tomcat源码分析--转
- MySql 里的IFNULL、NULLIF和ISNULL用法
- 使用Rancher搭建K8S测试环境
- 新增成功到编制为空bug_36 个JS 面试题为你助力,让面试更有力(面试必读)
- 同样版本的jstl,都是jstl1.2版本,有个有问题,另一个没有问题
- 阿里云Centos镜像源和EPEL源
- androidx86安装pc后无法联网_Ubuntu 16.04 安装显卡驱动后循环登录和无法设置分辨率的一种解决方案
- [Java] 蓝桥杯ADV-205 算法提高 拿糖果
- 浴血凤凰DNF自动辅助开发教程
- BarTender制作圆形标签的方法
- python中base函数_详细的python basemap中各函数的所有参量注释
- 以Crotex M3为例讲解stm32芯片内部原理
- 产品引流的方式有哪些?适合引流推广的平台有哪些?
- 关于联合体union的详细解释
- 【论文阅读】Adaptive Clustering-based Malicious Traffic Classification at the Network Edge
- 下一代安全管理平台NextSOC
- php中的网页漂浮代码,网页中上下漂浮的按钮JS代码-DEDE
热门文章
- 7年赚出两个阿里加两个腾讯,他是地表最强打工人!
- 这个“十一”长假,你是背“锅”出行吗?
- “腾讯持股比例提升”系误读!美团对外定增后腾讯持股比例降低
- 网红奶茶雪糕高价背后,到底是真好吃还是智商税
- 快手封禁网红殷世航:涉及炒作卖货、低俗表演等违规行为
- 男子拒绝春节带电脑回家工作被开除,最后结果十分舒适...
- 网易有道词典2019年度十大热词:Vlog、PUA等上榜
- 相机翻转设计的华硕旗舰ZenFone 6固件更新:新增“超级夜间模式”
- 自如回应南京租客事件:未对该房源进行过装修 配置的家具符合规定
- 元年·潮湃 首届搜狐5G峰会倒计时 参会大咖揭晓