在c中有指针和数组的说明

时间:2015-08-03 11:46:09

标签: c

我想知道* p = c,* q = c中可用的值是多少,因为c声明了一个数组++ q中可用的值,以及++ pI中的第二个forloop在turbo c中它给出输出,2 2 2 2 2 2 3 4 6 5在这里我无法按照进程。我请求堆栈团队给出解释。 。

main()
{
    int c[]={2.8,3.4,4,6.7,5};
    int j,*p=c,*q=c;
    for(j=0;j<5;j++)
    {
        printf(" %d ",*c);
        ++q;     
    }
    for(j=0;j<5;j++)
    {
        printf(" %d ",*p);
        ++p;     
    }
}

4 个答案:

答案 0 :(得分:1)

q是一个指针,您需要取消引用指针以获取值

printf(" %d ",*c);

应该是

printf(" %d ",*q);

在第一个循环中c是一个数组名称,并且有一个数组衰减到指针的概念,您可以取消引用并获取存储在数组中的值,但c在第一个循环中未被修改因此,您总是得到相同的值,而在第二个循环中,您通过执行p++

来移动指针

答案 1 :(得分:0)

printf(" %d ",*c);
               ^ c is an integer array not pointer .

正确

printf(" %d ",*q);

q是指针,应取消引用以获取它指向的值。

修改

int j,*p=c,*q=c;

所以这里类似于

int j,*p,*q=c;
p=c;

因此p指向c地址的数组c[0]的初始元素的地址。

它是递增的

   `++p`  // Pointer moves to the next int position (as if it was an array)
    //in this case increments to c[1] ,c[2] till c[n-1] in every iteration

注意 - 如果要增加指针的值,可以执行此操作++*p

答案 2 :(得分:0)

除非它是sizeof或一元&运算符的操作数,或者是用于在aa声明中初始化另一个数组的字符串文字,否则表达式类型&#34; T&#34;的N元素数组;将被转换(&#34;衰减&#34;)到类型为&#34的表达式;指向T&#34;的指针,并且表达式的值将是第一个元素的地址。阵列。

int c[]={2.8,3.4,4,6.7,5};

您已将c声明为int的数组,其大小取自初始值设定项中的元素数(5)。请注意,初始值设定项(2.8,3.4,6.7)中的浮点值将丢弃其小数部分(2,3,6)。如果需要浮点值数组,则必须将其声明为floatdouble而不是int

在声明中

int j,*p=c,*q=c;

c不是sizeof或一元&运算符的操作数,因此它被转换为指针表达式,其值是数组中第一个元素的地址,因此pq都使用c中第一个元素的地址进行初始化。在内存中,它看起来像这样(地址是凭空而来的,我们将假设4字节int,4字节指针和大端架构):

Item        Address            0x00  0x01  0x02  0x03
----        -------            ----  ----  ----  ----
   c        0x80001000         0x00  0x00  0x00  0x02
            0x80001004         0x00  0x00  0x00  0x03
            0x80001008         0x00  0x00  0x00  0x04
            0x8000100c         0x00  0x00  0x00  0x06
            0x80001010         0x00  0x00  0x00  0x05
   j        0x80001014         0x??  0x??  0x??  0x?? // ?? represents unknown byte value
   p        0x80001018         0x80  0x00  0x10  0x00
   q        0x8000101c         0x80  0x00  0x10  0x00

pq都包含c的第一个元素的地址。 j未显式初始化,因此其值不确定。

在你的第一个循环中,

for(j=0;j<5;j++)
{
    printf(" %d ",*c);
    ++q;     
}

解除引用 c(这是允许的;因为c不是sizeof或一元&的操作数运算符,它被转换为指针类型); *c相当于c[0],它的计算结果为c的第一个元素的值,即2。然后,您更新q的值以指向c的下一个元素,但您不会对其执行任何操作。更改q中的值不会影响c中的值。

在第二个循环中,

for(j=0;j<5;j++)
{
    printf(" %d ",*p);
    ++p;     
}

您正在打印p 指向的值。最初p指向c的第一个元素;每次循环时,p都会更新为指向c的下一个元素,有点像这样:

j    p              *p                
-    ----------     --
0    0x80001000      2
1    0x80001004      3
2    0x80001008      4
3    0x8000100c      6
4    0x80001010      5

第一个循环中q发生了同样的事情,你只是在print语句中没有使用它。

请注意,p++并不是简单地将{1}}中存储的值加1;指针算法将指向类型的大小考虑在内,以便pp++提前指向该类型的下一个元素。如果p的类型为*p(大小为1),则它将前进1个字节。如果char的类型是一个四字节整数,那么它将提前4个字节。

请注意,即使在大多数情况下表达式 *p可能会转换为指针类型,c指定的对象也不会一个指针。 c不会在任何地方存储地址。此外,c可能不是c++运算符的操作数,也可能不是赋值的目标;您可以更改每个--中存储的值,但不能更改c[i]本身的值。

答案 3 :(得分:0)

查看您的代码

首先是你的

1.你要声明数组并用一些值初始化它。

int *p=c;

int * p 和p = c; //第一个元素的数组存储地址的名称。

所以这里p是一个指针类型变量,它存储一个数组的起始地址。现在你正在做的第一个循环

 printf(" %d ",*c);// c contain address ,*c contain the value of that address(means value of zeroth address of array).

和你的递增'q'对c没有影响;

它打印'2'不是'2.8'因为它是整数性质。

现在处于第二个循环

printf(" %d ",*p); // it prints first element of array in first iteration 

然后你增加p的值;   现在看

++ p做什么?

第一个p指向数组的第0个地址现在p是一个int类型,所以当你现在递增它时,它会向前跳转到4个字节(假设为int size),并且在该地址中你的下一个数组元素即3存储。