关于printf造成指针*p乱码的问题

关于printf()影响指针*p结果的有关讨论,现摘取一篇网文。

int main()
{
    int stu[M][N] = {NULL};
    float* arr;
    float* MeanStuFun(int p[M][N]);
    int i,j;
    for(i=0;i<M;i++)
    {
        printf("please input the scores of NO.%d
",i+1);
        for(j=0;j<N;j++)
            scanf("%d",&stu[i][j]);
    }
    arr=MeanStuFun(stu);
printf(" every student's mean score is: ");
for(i=0;i<M;i++) printf("%8.2f",*(arr+i)); return 0; } float* MeanStuFun(int p[M][N]) { int i,j; float arr[M]={NULL}; float mean=0; for(i=0;i<M;i++) { for(j=0;j<N;j++) mean=mean+p[i][j]; arr[i]=1.0*mean/N; mean=0; } return arr; }

上面第一个printf()可以输出标题,但接下来的printf()输出的值为乱码。如果将第一个printf()移到arr=MeanStuFun(stu)前,则第二个printf()可以输出正确的结果,接下来的printf()依然得不到正确的结果。这就需要使用#include<stdlib.h>中的malloc函数。此函数用在子函数中,但作用于全局,专门为指针在中开辟一个特定大小的空间,在return 0之前需要用free()函数对占据内存进行释放,这样就可以避免printf等对指针的影响。释放时需要将malloc分配空间的首地址返回给主函数的指针变量,然后即可在主函数中进行内存的释放。

这是什么原因呢? 调用函数printf前先要将形参压,这时候要计算*arr。所以,第一条printf语句已经把参数算出来并放到栈顶保存了。然后调用printf函数(函数调用需要用到栈建立访问连和控制链,而原来的函数function执行完了,原本f是在栈顶的,所以,函数f的栈空间释放。数组空间也被释放),printf占用了栈,所以,把原来函数f的栈空间内容修改了。所以,第一条printf语句是可以得到结果的。后面因为arr空间的内容已经被修改,所以,之后的printf语句都得不到结果。
顺便再解释一下printf("%s ",*arr);得到的为什么是乱码。
正如上面所说,先计算参数*arr的值保存栈顶。保存的值为arr的地址。然后调用printf函数,把栈顶空间内容修改了。虽然保存了地址,但是原来的内容已经修改了,所以得不到结果。

原文地址:https://www.cnblogs.com/2Bthebest1/p/7102463.html