3

I know the C language has dynamic length strings whereby it uses the special character null (represented as 0) to terminate a string - rather than maintaining the length.
I have this simple C code that creates a string with the null character in the fifth index:

#include <stdio.h>
#include <stdlib.h>
int main () {   
  char * s= "sdfsd\0sfdfsd";
  printf("%s",s);
  s[5]='3';
  printf("%s",s);
  return 0;
}

Thus, a print of the string will only output up to the fifth index. Then the code changes the character at the fifth index to a '3'. Given my understanding, I assumed it would print the full string with the 3 instead of the null, as such: sdfsdsdfsd3sfdfsd

but instead it outputs: sdfsdsdfsd

Can someone explain this?

Favn Hghksd
  • 321
  • 6
  • 14
  • 7
    String literals cannot be changed, an attempt to do so creares undefined behaviour. – n. m. could be an AI Oct 22 '17 at 05:04
  • 1
    Try `char *s = (char[]){ "sdfsd\0sfdfsd" };` (using a *compound literal* to initialize `s` as a *pointer to array of char*) or `char s[] = "sdfsd\0sfdfsd";` to initialize as an array of char. – David C. Rankin Oct 22 '17 at 05:16
  • Possible duplicate of [Why do I get a segmentation fault when writing to a string initialized with "char \*s" but not "char s\[\]"?](https://stackoverflow.com/questions/164194/why-do-i-get-a-segmentation-fault-when-writing-to-a-string-initialized-with-cha) – aschepler Oct 22 '17 at 05:49

4 Answers4

2

This program exhibits undefined behavior because you modify a read-only string literal. char* s = "..." makes s point to constant memory; C++ actually disallows pointing non-const char* to string literals, but in C it's still possible, and we have to be careful (see this SO answer for more details and a C99 standards quote)

Change the assignment line to:

char s[] = "sdfsd\0sfdfsd";

Which creates an array on the stack and copies the string to it, as an initializer. In this case modifying s[5] is valid and you get the result you expect.

Eli Bendersky
  • 263,248
  • 89
  • 350
  • 412
1

This operation has failed:

s[5] = 3;

You're trying to change a string literal, which is always read-only. My testing shows the program exited with segfault:

Segmentation fault (core dumped)

You should store it in an array (or allocated memory) before any attempts to change it:

char s[] = "sdfsd\0sfdfsd";

With the above change, the program works as intended.

iBug
  • 35,554
  • 7
  • 89
  • 134
1

String literals can not be changed because the compiler put the string literals into a read-only data-section (but this might vary by underlying platform). The effect of attempting to modify a string literal is undefined.

In your code:

char * s= "sdfsd\0sfdfsd"

Here, s is char pointer pointing to a string "sdfsd\0sfdfsd" stored in read-only memory, making it immutable.

Here you are trying to modify the content of read-only memory:

s[5]='3';

which leads to undefined behavior.

Instead, you can use char[]:

#include <stdio.h>

int main () {
  char a[] = "sdfsd\0sfdfsd";
  char * s = a;
  printf("%s",s);
  s[5]='3';
  printf("%s\n",s);
  return 0;
}
H.S.
  • 11,654
  • 2
  • 15
  • 32
-1
#include <stdio.h>

int main(){
    char x[10] = "aa\0a";
    x[2] = '1';
    puts(x);

    printf("\n\n\nPress any key to exit...");
    getch();
    return 0;
}

Output: aa1a

iBug
  • 35,554
  • 7
  • 89
  • 134