趁着做操作系统,也学学C,指针是真的绕。
++b和&b+1
#include <stdio.h>
void foo(int b[][3]){
//++b; // b + 1*sizeof(b[0]) 故只跳过了一行将a[2][1]变成了9
&b+1; //b + 1*sizeof(b) 故跳过了所有已有值,原有值不变
b[1][1] = 9;
}
void main(){
int a[3][3] = {{1, 2, 3}, {4, 5, 6}, {7, 8, 9}};
foo(a);
printf("%d", a[2][1]);
char *str[80]; //str[80]
str[80] = "abcdefg";
}
strlen()统计字符个数及strcpy()复制
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
char * GetWelcome(void){
char * pcWelcome;
char * pcNewWelcome;
pcWelcome = "Welcome to Huawei Test";
pcNewWelcome = (char *)malloc((strlen(pcWelcome)+1)*sizeof(char)); //1 strlen()统计字符个数,不含结尾符'\0',所以这样子分配会少一个字节。
if(NULL == pcNewWelcome){
return NULL; //2
}
strcpy(pcNewWelcome, pcWelcome); //3 由1处,既然新分配的空间少了一个字节,你用原来的来复制到新的里?能装下吗?不能。
return pcNewWelcome; //4
}
int main(int argc, char const *argv[])
{
printf("%s\n",GetWelcome());
return 0;
}
scanf()和printf()
#include "stdio.h"
int func(int x, int y) { return (x + y); }
main() { // 默认int返回类型
int a = 1, b = 2, c = 3, d = 4, e = 5;
printf("%d\n", func((a + b, b + c, c + a), (d, e))); // 逗号分隔只看最右一个
int x, y;
scanf("%2d%*4s%2d", &x, &y); // 取两位跳四位再取两位
printf("%d\n", y - x);
unsigned short A = 10;
printf("~A = %u\n", ~A); // 0xfffffff5无符号取反,补码
char C = 128;
printf("C=%d\n", C);
char ch = 'a';
int k = 12;
printf("%x,%o,", ch, ch, k); // 最右一位忽略
printf("k=%%d\n",k); // %%d转义 %d
char *p1 = "hello";
char *p2 = "world";
char *p3 = "a piece of cake";
char *str[] = {p1, p2, p3};
printf("%s", str[0]); // 字符串需要用地址作为数组输出,字符char可以直接值输出:printf("%c",*str[0])
return (0);
}
杂七杂八
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
struct node
{
char data;
struct node *next;
} a, b, *p = &a, *q = &b;
double array[10];
int c = 1, d = 2;
void funl(int c, int d) { printf("%d%d", c, d); }
void fun2() {
c = 3;
d = 4;
}
void Test(void)
{
char *str = (char *) malloc(100);
strcpy(str, "hello");
free(str);
if (str != NULL)
{
strcpy(str, "world\n");
printf(str);
}
}
int main(int argc, char const *argv[])
{
p->next=&b; // 指针不能直接用.,应该(*p).next
int a[] = {1, 2, 3, 4};
int *b = a;
*b += 2;
*(b + 2) = 2;
b++;
printf("%d,%d\n", *b, *(b + 2)); // 2,4
printf("%d\n",sizeof(array)/sizeof(array[0])); // 10,字符串最后才会有\0
funl(c,d);
fun2();
printf("%d%d\n", c, d); // 局部变化生效
Test(); // world
int e = 0xabcd1234;
char f = ((char*)&e)[0];
printf("%x",f); //34 小端存储
return 0;
}
const、有无符号的比较、64位机指针大小
#include<stdio.h>
int main(){
int i = 10;
int j = 1;
const int *p1;//(1)
int const *p2 = &i; //(2)
p2 = &j;//(3)
int *const p3 = &i;//(4)
*p3 = 20;//(5)
//*p2 = 30;//(6) *前const 值不可变
//p3 = &j;//(7) *后const 地址不可变
//int x = 5;
//const int &q=x; //&q赋值初始化常量也会报错
int x = -1;
unsigned int y = 2;
if(x > y) { //有符号数与无符号数比较,会自动转换为无符号数,-1补码最高那位是1,比2大太多了
printf("%s\n","x is greater");
} else {
printf("%s\n","y is greater");
}
char *str1 = "hello";
short * p4;
int p5[2];
printf("%d\n",sizeof(str1)); //8 64位机指针都为8位
printf("%d\n",sizeof(p1)); //8 64位机指针都为8位
printf("%d\n",sizeof(p2)); //8
return 0;
}
指针传递、补码、fork
#include<stdio.h>
void foobar(int a, int *b, int **c)
{
int *p = &a;
*p = 101;
*c = b; // p这时指向了b的地址
b = p;
}
int main()
{
//int arr[]; 必须定义数组个数,分配内存
int a = 1;
int b = 2;
int c = 3;
int *p = &c;
foobar(a, &b, &p);
printf("a=%d, b=%d, c=%d, *p=%d\n", a, b, c, *p); //a=1, b=2, c=3, p=2
char x = 0xFFFF;
printf("%d\n",x--); // char1个字节8bit,只能存2个十六进制位,也就是0xFF 首位符号位为1 补码为1111 1111 原码为1000 0001 即-1
printf("Hello");
fork();
printf("Hello"); // 4次Hello,fork本来只fork后面的语句,但因为前面的前面没有\n清缓存
return (0);
}
arr[15]与*str、常量拼接与Segmentation fault
#include<stdio.h>
#include<string.h>
void main(){
short *p,*q;
short arr[15] = {0};
p = q = arr;
p++;
printf("%d,", p - q); //1
printf("%d,", (char*)p - (char*)q); // short 2个字节,强转char以后,2
printf("%d", sizeof(arr) / sizeof(*arr)); // 15*2 / 2 即数组元素个数(区别字符串和strlen) *arr是首位的值,也就是short,两个字节
char *p1 = "123", *p2 = "ABC";
char str[50]= "xyz";
//strcpy(str + 2, strcat(p1, p2)); // 常量无法拼接 segmentation fault
printf("%s\n",str);
}