2013-05-20 35 views
3

请考虑此代码。了解字符串和数组

int main() 
{ 
    char *s, *t; 

    s = malloc(4 * sizeof(char)); 
    strcpy(s, "foo"); 
    t = s; 
    printf("%s %s\n", s, t);   // Output --> foo foo 
    strcpy(s, "bar"); // s = "bar" 
    printf("%s %s\n", s, t);   // Output --> bar bar 
} 

有2个字符串st。首先,我将s设置为"foo",然后将t指向s。当我打印字符串时,我得到了foo foo

然后,复制"bar"s并再次打印,我得到bar bar

为什么t的值在这种情况下发生了变化? (我复制"bar"s为什么t改变)。


现在,当我改变strcpy(s, "bar")s = "bar" -

int main() 
{ 
    char *s, *t; 

    s = malloc(4 * sizeof(char)); 
    strcpy(s, "foo"); 
    t = s; 
    printf("%s %s\n", s, t); // Output --> foo foo 
    s = "bar" 
    printf("%s %s\n", s, t); // Output --> bar foo 
} 

此代码给我foo foobar foo

为什么在这种情况下没有改变?

+3

**版主说明**:玩的很好。保留主题的意见(意思是他们应该要求澄清)。如果你想打开关于这个问题的优点的讨论,去[这里](http://meta.stackoverflow.com)。 –

+1

我已经删除了你的问题的第二部分,如果你仍然想问它,请另写一篇文章。你应该每个帖子只问一个问题。 – sashoalm

回答

12

这是undefined behaviour,这意味着任何事情都有可能发生:

char *s, *t; 
strcpy(s, "foo"); 

strcpy()在内存中写入一个随机位置,因为s是一个未初始化的指针。


编辑修正未定义行为后)

问题1 - 为什么在这种情况下,T改变价值? (我复制了“酒吧”为什么没有改变)。

这是一个指针赋值:

t = s; 
两个 t

和结果s指向相同的内存,这是malloc()并分配给s更早。通过ts可以看到对该内存的任何更改。

问题2 - 为什么在第二种情况下不会发生变化?

此字符串文字"bar"的地址分配给s

s = "bar"; 

所以现在ts不指向同一个内存位置。 t指向较早的malloc()并分配给s的内存(因为指针分配为t = s;)。

strcpy()=非常不同:

  • strcpy()副本字符由它的第一个参数
  • 分配,=所指定的存储器地址,改变其中指示器保持
+0

好的,我现在有'malloc' ...仍然是同样的问题。 – ShuklaSannidhya

+0

为什么在第二种情况下没有改变? – ShuklaSannidhya

+0

所以每当我创建一个字符串文字,它会在内存中创建一个新的位置?像's =“bar”',会先在一个新位置创建一个''bar'',然后将它分配给's'? – ShuklaSannidhya

2
地址
strcpy(s, "foo"); 

份数foo指向由s指向的内存位置 t = s; 现在,ts都指向同一个位置 因此,相同的输出

现在,您复制bars。由于ts都指向相同的位置。因此,同样的输出。


高达此行一切都是相同

s = "bar" 

您创建一个字符串常量bar。并将其地址分配给s。它的一个pointer它可以指向任何内存位置。不一定是原来的。

现在,

sbart仍然在较前位置是在一开始指出,因此输出

2

一个简单的方法来了解可能如下: -

 s = malloc(4 * sizeof(char)); // this will be interpreted as follows 
     s = 123 ------------>| | | | | //some garbage values at these location 
          123 124 125 126 // some random address chosen. 

     strcpy(s, "foo") ; // it copies at the address provided by s i.e. 
          |'f'|'o'|'o'|'\0'| 
           123 124 125 126 

     t = s;  this statement means t it pointing to address = 123 

     strcpy(s, "bar"); // this statement copies at given address it means it will override previous value . i.e 
          |'b'|'a'|'r'|'\0'| 
          123 124 125 126 

现在仍然指向地址123这就是为什么t,s都打印吧。

 s = "bar" // this will assign a new address to s which is base address of "bar" string . i.e .   
          |'b'|'a'|'r'|'\0'| 
          321 322 323 324  

现在s将包含地址321,而t的值为123,这就是为什么s和t给出不同的值。