-5

I know that this is simple. I tried looking for an answer in stackoverflow before asking but couldn't find an answer.

char str[5], new_str[5];
int i, len;

printf("Enter a string: ");
scanf("%s", str);
len = strlen(str);

for (i = 0; i < len; i++){
    new_str[i] = str[i];
}

printf("Result: %s", new_str);

I get:

Enter a string: 1234
Result: 1234╠╠╠╠╠╠╠╠╠╠╠1234

I know how to do it properly(using malloc) but I am trying to understand why this is output happened.

Lee
  • 781
  • 2
  • 11
  • 31
  • 2
    "I know how to do it properly ..." No, you don't! Read how C strings are terminated. And limit the number of chars accepted by `scanf` to what is available in the buffer. – too honest for this site Aug 14 '15 at 17:57
  • 2
    Strings need to be null terminated. `char str[5]` can only hold 4 characters plus a trailing null. You're not handling the strings correctly because `12345` has 5 characters so `str` has no null so all hell breaks loose (welcome to 'undefined behaviour' — avoid it like the plague it is). Also, although you compute `len = strlen(str);`, you never use that value. – Jonathan Leffler Aug 14 '15 at 17:57
  • 1
    The string is not long enough. You entered 5 characters, so it needs `char str[6];` – Weather Vane Aug 14 '15 at 17:57
  • 1
    Again STOP DECLARING STUPID CHAR ARRAY SIZES FOR TEXT LINES unless you are on some RAM-retricted embedded system. What possessed you to type '5' instead of, say, '256'??? WHY? – Martin James Aug 14 '15 at 18:01
  • I forgot about the null character. You can delete the question... – Lee Aug 14 '15 at 18:02
  • 1
    You would do best to limit the input string: `scanf("%4s", str);` (and test that it worked). You could also use `printf("Result: %.5s\n", str);` and that would work better. However, when you enter the overlong string on the input (even just one byte too long), you are not guaranteed anything. You might be OK, you might not; it is only safe to assume you will not and prevent the overflow. – Jonathan Leffler Aug 14 '15 at 18:02
  • @Lee I believe _you_ can delete the question, but most of the rest of us cannot unless it goes through a potentially lengthy voting process. I've voted to close it; if 4 more agree then it gets closed and then we can vote to delete... or you could directly delete. – mah Aug 14 '15 at 18:04
  • This is the second one of these 'I'll just declare a really small array 'cos.... nobody knows' today. http://stackoverflow.com/questions/32012571/why-does-the-stack-get-corrupted – Martin James Aug 14 '15 at 18:04
  • @MartinJames: maybe the second one today; certainly not the second one in the history of SO. I usually 4096 as the size for 'lines' of input, partly for the shock value. POSIX sets LINE_MAX to 2048, IIRC, which is the minimum length that is acceptable for the longest line that the system accepts. That said, 256 is a huge step in the right direction (heck, even 80 would be better, though that's a very imperfect value to be using too). – Jonathan Leffler Aug 14 '15 at 18:05
  • @JonathanLeffler I suspect that most of these are disguised no-effort homework questions. – Martin James Aug 14 '15 at 18:42
  • ╠ is 0xCC in codepage 437, and [MSVC fills 0xCC to uninitialized memory to help debugging](https://stackoverflow.com/q/370195/995714). That means you've accessed uninitialized memory. You can find tons of questions about ╠ and 0xCC here on SO – phuclv Aug 18 '18 at 10:55

3 Answers3

3

The variable new_str has no '\0' symbol at the end of it because it's an array but not a "string".

The call to printf("%s", new_str); prints the whole string up to the '\0' symbol, which ends a string.

After the input shown, str is equivalent to {"1","2","3","4","5","\0"} and new_str is equivalent to {"1","2","3","4","5"} because you only copied 5 symbols. Because of that, printf prints other symbols after 12345 (new_str) which are in the next cells of memory, up until it does find a null byte. And that's undefined behaviour.

Jonathan Leffler
  • 730,956
  • 141
  • 904
  • 1,278
Eduard
  • 475
  • 4
  • 14
0

You need to add the null terminator to the string.

i.e. add

new_str[i] = 0;

Before the

printf....

Anyway perhaps

for (i = 0; i < 5; i++){

should be

for (i = 0; i < len; i++){

and check out the page for scanf so as to not overrun the buffer

Ed Heal
  • 59,252
  • 17
  • 87
  • 127
0

You enter 12345 in str, no space for '\0',thus giving UB.

Restrict input in str like this -

  scanf("%4s", str);   

And this loop-

  for (i = 0; i < 5; i++){
     new_str[i] = str[i];
 }

Size of both arrays is 5 but strings in C are null terminated so this loop should go till i=4.

And new_str[4]='\0'; should be set.

ameyCU
  • 16,489
  • 2
  • 26
  • 41