同一变量的不同内存地址

时间:2014-03-13 17:54:04

标签: c++ memory-management

为什么两个k的地址不同,如以下代码的输出所示?

#include<cstdio>
#include<cstring>
#include<cmath>
#include<vector>
using namespace std;
int anu[1000000];
int calc(int a,int b,int c,int d)
{
    long long int k;
    k=(long long int)a*d*d+b*d+c;
    return k%1000000;
}
int main()
{
    int t,n,i,a,b,c,d,k;
    scanf("%d",&t);
    while(t--)
    {   
        scanf("%d %d %d %d %d",&n,&a,&b,&c,&d);
        memset(anu,0,sizeof(int)*1000000);
        anu[d]=1;
        vector<int> anu1;
        anu1.push_back(d);
        for(i=1;i<n;i++)
        {
            k=calc(a,b,c,anu1[i-1]);
            anu1.push_back(k);
            anu[k]=anu[k]?0:1;
        }
        d=0;k=0;
        printf("address of k=%d ",&k);
        for(i=0;i<1000000;i++)
        {
            if(anu[i])
                {
                if(d%2)
                k-=i;
                else
                k+=i;
                d++;
            }
        }
        printf("%d address of final k=%d\n",abs(k),&k);
    }
    return 0;
}

输入: 1 1 1 1 1 1

输出: 地址k = -1074414672 0地址最终k = 1072693248

3 个答案:

答案 0 :(得分:5)

当我使用clang ++构建(尽可能多地启用警告)时,我会收到以下警告:

k.cpp:45:45: error: call to 'abs' is ambiguous
        printf("%d address of final k=%d\n",abs(k),&k);
                                            ^~~
/usr/local/include/c++/v1/cmath:660:1: note: candidate function
abs(float __x) _NOEXCEPT {return fabsf(__x);}
^
/usr/local/include/c++/v1/cmath:664:1: note: candidate function
abs(double __x) _NOEXCEPT {return fabs(__x);}
^
/usr/local/include/c++/v1/cmath:668:1: note: candidate function
abs(long double __x) _NOEXCEPT {return fabsl(__x);}
^

这是因为您没有包含<cstdlib>来声明abs的整数版本。如果没有这个包括编译器必须猜测它应该使用哪个函数,并且它似乎选择不好,因为它从<cmath>中选择一个浮点变体。这会导致您覆盖printf调用中的下一个参数。

在构建程序时,我建议每个人尽可能多地发出警告,他们通常会指出像这种情况一样的未定义行为。

答案 1 :(得分:2)

如果不取k变量的地址,则允许编译器使用寄存器来保存k的值。

对于大多数处理器,寄存器没有物理地址。它们不在CPU地址空间中。

通过打印k变量的地址,您告诉编译器要么将变量存储在内存中,要么让编译器生成地址。

并非所有变量都需要存储在可寻址存储器中;它们可以存储在寄存器中。

答案 2 :(得分:1)

  1. 您应该使用%p
  2. 打印指针
  3. abs()返回浮点数,在打印前将其转换为int解决问题
  4. 该行正确:

    printf("%d address of final k=%d\n",(int)abs(k),&k);