逻辑推理:可以看出,中间的那个人可能是“诚实的家伙”或者“说谎的家伙”或者“犹豫不决的”,这里形成悖论;根据推理,
假设中间为犹豫不决的,那么左右两边因为至少有一句是真的,而左右都没说中间是“犹豫不决的”,那么假设不成立;
假设中间为诚实的家伙,那么很显然,假设不成立;
推出中间为说谎的家伙,则右边为诚实的家伙,左边是犹豫不决的;
解:
指针函数:int* fun(int x,int y);
函数指针:int (*fun)(int x,int y);
可以简单粗暴的理解为,指针函数的*是属于数据类型的,而函数指针的星号是属于函数名的。
再简单一点,可以这样辨别两者:函数名带括号的就是函数指针,否则就是指针函数。
通过括号,可以看出后面两个是(int * (*)(int *,int*),int*)是参数,分别是函数指针 int * (*)(int *,int*) 和 int* ;
形式:typedef 返回类型(*新类型)(参数表)
功能: 定义新的类型。
typedef char (*PTRFUN)(int);
PTRFUN pFun;
char glFun(int a){ return;}
void main()
{
pFun = glFun;
(*pFun)(2);
}
第一句就是定义了一种PTRFUN的类型,并定义这种类型为指向某种函数的指针,这种函数以一个int为参数并返回char类型。后面就可以像使用int,char一样使用PTRFUN了。
第二行的代码便使用这个新类型定义了变量pFun,此时就可以像使用形式1一样使用这个变量了。
memcpy()函数内存重叠的实现:
如果目标地址大于源地址,先拷贝高位源地址。
如果目标地址小于源地址,先拷贝低位源地址。
待定 !!
待解答
(宏定义只是单纯地展开,此处得2*3,和3+2也没有计算,直接代入展开)
(因为在计算机系统中,数值一律用补码来表示和存储。所以uc其实是-1的补码,即11111111,而_in >>24^uc 先右移24位,得 1001 1001,再和uc进行位异或,得0110 0110可得到0x55。)
#define MIN(A,B) ((A) <= (B) ? (A) : (B))
注意:宏定义只是展开,要谨慎把宏、参数用括号包含起来!!
凡是指针要看多少位的机器!!ss1,q3都是指针的大小;
ss2---11, q1---4 , q2---3 (自动补上’\0’);
段错误。原因:p1,p2指向常量字符串,不能对只读进行strcat操作,字符串常量内容不能被修改。
解:只要是涉及到编写函数就要考虑周全,如传参是指针,就要判断是否为空,若传递是字符串,考虑传参是否是只读,内容是否可以修改。
此处的strcpy,考虑三点:
(1)不受限制的字符串函数都是以’\0’为结尾标记来判断的,因此输入参数必须包含‘\0’
(2)必须保证目标字符数组的空间足以保存整个源字符串
(3)strcpy(dest,src)函数是把从src地址开始且含有NULL结束符的字符串复制到以dest开始的地址空间中,而且src和dest所指内存区域不可以重叠。这就要求dest必须有足够的空间来容纳src的字符串
参考代码:
char* my_strcpy(char *dest,const char *src)
{
char *cp=dest;
assert(src && dest);
while(*dest++ = *src++); //或者while((*dest++ = *src++) != ‘\0’);
//执行完这句话,那个‘/0’也已经赋值啦,
return cp;
}
函数的传参和返回:
判断大小端问题:
注意:是“字节”,不是“位”
计算“1”的个数:
3.写一个函数计算long变量有多少位的bit值为1:
可以看出,这是一种消“1”法,每与上一次自己减一的数,就消去一个“1”。如1001 & 1000 = 1000 ; 1000 & 0111 = 0