2017-06-14 30 views
-3

有人可以向我解释为什么从scanf()用户接收的ints存储在相隔8h的地址,即使大小我的64位机器上有4个字节的int?这是与内存中的对齐?c程序 - 为什么整数存储间隔8小时,即使它们占用4个字节

#include <stdio.h> 
void main() { 

    int *a; 
    int i, n; 



    printf(" Input the number of elements to store in the array : "); 
    scanf("%d",&n); 

    printf(" Input %d number of elements in the array : \n",n); 

    printf("size of on int is %d\n", sizeof(i)); 

    for(i=0;i<n;i++) { 
     printf(" element - %d : ",i+1); 
     printf("address of a is %p\n", &a+i); 
     scanf("%d",a+i); 
    } 

    return 0; 

} 


Input the number of elements to store in the array : 3 
Input 3 number of elements in the array : 
size of on int is 4 
element - 1 : address of a is 0x7ffda5cf8750 
6 
element - 2 : address of a is 0x7ffda5cf8758 
5 
element - 3 : address of a is 0x7ffda5cf8760 
2 
+1

'%d'需要一个'int'。 'sizeof'产生'size_t' - >未定义的行为。 – Olaf

+1

'&a'取指针的地址,指针需要8个字节。您在代码中还有其他问题需要担心,比如写入无效位置('a'没有指向任何有效位置!) –

+1

'printf(“地址是%p \ n”,(void *)(a + i));'会通过sizeof(int)'(4)显示指针。 –

回答

5
#include <stdio.h> 
void main() { 

    int *a; 
    int i, n; 

有以下省略你的任何代码?如果不是,a现在是一个未初始化的指针,具有不确定的值。

printf("address of a is %p\n", &a+i); 

在这里,你需要使用&运营商a地址。结果是指向a,IOW指向指针的指针。一个64位系统上的指针大小是8,所以这应该回答你的问题。

scanf("%d",a+i); 

在这里你写了一些“随机”的内存位置。这是不确定的行为


供您参考,为你似乎什么固定的程序想做的事:

#include <stdio.h> 
#include <stdlib.h> // <- needed for malloc()/free() 

// use a standard prototype, void main() is not standard: 
int main(void) { 

    int *a; 
    int i, n; 

    printf(" Input the number of elements to store in the array : "); 
    if (scanf("%d",&n) != 1) 
    { 
     // check for errors! 
     return 1; 
    } 

    // allocate memory: 
    a = malloc(n * sizeof(int)); 

    for(i=0;i<n;i++) { 
     printf(" element - %d : ",i+1); 
     if (scanf("%d", a+i) != 1) 
     { 
      // again, check for errors! 
      return 1; 
     } 
    } 

    // [...] 

    // when done, free memory: 
    free(a); 

    return 0; 
} 

学习如何做输入更有力,对scanf()阅读文档,fgets()strtol() ...我准备了a little document,但网上有很多其他资源可用,例如this FAQ on SO

+0

另外,如果您使用的是Microsoft编译器,请查看防止缓冲区溢出的更安全的scanf版本(例如s_scanf)。 – Neil

+3

@Neil no,'scanf_s'是完全不必要的,只是试图锁定供应商。对于转换为字符串,只需使用'scanf()'以适当的字段宽度。 –

+0

真的吗?所以scanf(“%s”,charArray)中没有可能的缓冲区溢出? – Neil

相关问题