C 指针运算(mooc)

  • *p++; // ++ 的优先级比* 高,这条命令意思是取出p所指的数据,顺便把p移到下一个位置去。 常用于数组连续空间的操作。
  • 指针可以做加减运算,比较运算 >,>= ,<, <=, != ,==不可以做乘除运算,因为毫无意义。
  • 0地址:
    • 内存中有0地址,但是0地址通常是一个不能随便碰的地址。所以指针不应该具有 0 值。
    • 因此可以用0地址来表示特殊的事情:(1)返回的指针是无效的。(2)指针没有被真正初始化(先初始化为0)
    • NULL是一个预定义的符号,表示0地址。 有的编译器不愿意你用0来表示 0 地址
  • 指针的类型:无论指向什么类型,所有的指针大小都一样,因为都是地址。  但是指向不同类型的指针是不能直接相互赋值的。
    int *p;
    char *q;
    // 如果把q的地址赋给p,那么*p=0;就会把q指向的地址连续4个字节单元全部赋值为0,而不是1个字节。这样会导致bug。
  • 指针的类型转换:void* 表示不知道指针指向什么东西。计算时与char* 相同,但不相通。
  • int  *p = &i;  
    void * q = (void*) p;
     // 转换p的类型 并没有改变p所指的变量的类型,即i的类型还是int。q不会把i当作是int 类型,而是认为i 是void。p还是认为i 是int。

    通过下面测试代码也可以知道

    #include <stdio.h>
    
    int main()
    {
       /* 我的第一个 C 程序 */
       int i = 5;
       int *p = &i;
        void * q = (void *) p;
        printf("p=%p
    ",p);
        printf("q=%p
    ",q);
        printf("&i=%p
    ", &i);
        printf("sizeof(p)=%d
    ", sizeof(p));
        printf("sizeof(q)=%d
    ", sizeof(q));
        printf("sizeof(i)=%d
    ", sizeof(i));
        printf("sizeof(*p)=%d
    ", sizeof(*p));
        printf("sizeof(*q)=%d
    ", sizeof(*q));
       return 0;
    }
    
    // output
    p=0x7ffd659a756c
    q=0x7ffd659a756c
    &i=0x7ffd659a756c
    sizeof(p)=8
    sizeof(q)=8
    sizeof(i)=4
    sizeof(*p)=4
    sizeof(*q)=1
    View Code
  • 指针的应用:
    • 需要传入较大的数据时用作参数
    • 传入数组后对数组做操作
    • 函数返回不止一个结果
    • 动态申请内存
  • free 释放的内存空间必须是之前申请来的,而且必须是申请的内存的首地址。意思是不能把其他变量的地址给free掉(不是申请来的)。
    int *p = (int *) malloc(10*sizeof(int));
    p++;
    free(p);  //error
    // 传入的不是首地址

    对于小程序而言,忘记free 影响不大,程序运行期间造成的内存泄露在程序运行完以后,操作系统会清理。但是对于大程序,服务程序(常驻的,一直运行)忘记free会导致及其严重的后果。因为程序没有运行结束,操作系统也不会清理的。

原文地址:https://www.cnblogs.com/bneglect/p/14643193.html