sizeof
sizeof是运算符,不是函数
给出某个类型或变量在内存中占据的字节
数
对sizeof的处理是在编译阶段进行
int a=6;
printf("sizeof double=%d\n",sizeof(double));
printf("sizeof int=%d\n",sizeof(int));// sizeof后面是类型或者表达式时, 要加()
printf("sizeof a=%d\n",sizeof a);
// 指针变量的sizeof值与指针所指的对象没有任何关系,所有的指针变量都是8字节
sizeof(2+3.14);// 3.14的类型为double,所以等价于sizeof(double);
&
// 它的操作数必须是一个变量.他把这个变量的地址拿出来给你.
// &nurse表示变量nurse的地址
printf("%p\n",&i);// 输出变量i的地址,16进制
int i;int *p=&i; // p的值是i的地址
int *p,q; // p是一个指向int的指针,q是一个int型变量
arithmetic
All arithmetic involving pointers is scaled based on the data type that the pointers involved point to.
The effect of p+n
where p
is a pointer and n
is an integer is to compute the address equal to p
plus n
times the size of whatever p
points to.
incrementing a char* adds 1
incrementing an int* adds 4
incrementing a double* adds 8
Subtract one pointer from another.The two pointers must have the same type.
The result is an integer value, equal to the numerical difference between the addresses divided by the size of the objects pointed to.
// 指针变量p1和p2都指向同一数组中的元素,p2-p1的值是二者所指数组元素的序号之差
// 两指针的关系运算(指向同一数组中的元素时)
p<q // p在q之前,表达式为1,反之为0.
p>q // p在q之后,表达式为1,反之为0.
p++;// 使P指向下一元素
*p++;// the expression *p++ is parsed as *(p++), and not as (*p)++.
int b[5];
void test_ptr(){
int *ptr1 = b;// conversion to &b[0]
int *ptr2 = &b[2];
cout<<ptr2 - ptr1<<endl;//output:2
}
Void pointers
// Unlike ordinary pointers, you can't derefence a void * pointer or do arithmetic on it, because the compiler
// doesn't know what type it points to.
It is permitted to assign to a void * variable from an expression of any pointer type;conversely,a void * pointer value
can be assigned to a pointer variable of any type.
// no need to explicit cast
int *block;
block = malloc(sizeof(int) * 12);// void * converted to int * before assignment
free(block);// int * converted to void * before passing to free
variant
char **ptr;//ptr指向的是一个char*类型的变量
// 指针数组(是一个数组)
int *a[5];//数组中的元素都是int*
// 数组指针(是一个指针)
int (*ptr)[5];//pointer to array 5 of int,此时ptr+1是移动20个字节(int是4字节)
char (*ptr)[5];//pointer to array 5 of char
// 指针函数
返回指针类型的函数
// 函数指针
指向函数的指针
int (*p)(int,int);//pointer to function (int, int) returning int
int (*errfun)(const char *,int);//pointer to function (pointer to const char, int) returning int
void (*fun)(void);//pointer to function (void) returning void
int (*fun)(void);//pointer to function (void) returning int
常见错误
// 本地变量没有默认初始值,所指的地方非法时,程序就会崩溃
char *string;
scanf("%s",string);// scanf接收一长串字符后,按string指向的地址一一往后填字符,最后自动加上\0
// 这样是可以的
char p[20];scanf("%s",p);
char *p=(char *)malloc(10*sizeof(char));scanf("%s",p);
char *p="hello,C";// OK
// 这样是错误的
// p并没有初始化指向,可能会指向一个不能操作的地址
int *p;*p=12;
// The pointer variable answer, which is handed to gets() as the location into which the response should be stored,
// has not been set to point to any valid storage.
int main(){
char *answer;// we cannot say where the pointer answer points.
printf("Type something:\n");
gets(answer);
printf("You typed \"%s\"\n", answer);// Segmentation fault
}
https://c-faq.com/decl/spiral.anderson.html
https://c-faq.com/malloc/malloc1.html
https://faculty.cs.niu.edu/~mcmahon/CS241/Notes/arrays_and_pointers.html
https://cdecl.org/
https://www.cs.yale.edu/homes/aspnes/classes/223/notes.html#voidPointers
https://www.cs.yale.edu/homes/aspnes/pinewiki/C%282f%29Pointers.html