Take the 2-minute tour ×
Stack Overflow is a question and answer site for professional and enthusiast programmers. It's 100% free, no registration required.

I am new to programming. I am learning C as my first programming language. I found something strange to understand.

I have learnt that in C we can represent a String as a sequence of characters like this (using a char array):

char status[10] = "Married";   

I have learnt that the problem of this approach is that we have to tell the size of the status array during compilation.

But now I have learned we can use a char pointer to denote an string like -

char status[10] = "Married";
char *strPtr;
strPtr = status;

I don't understand it properly. My questions are -

  1. How can I get char at index 4 (that is i in Married) using the strPtr?

  2. In status there is a null character (\0) at the end of the string represented by the char array - M-a-r-r-i-e-d-\0. So by using the null character (\0) we can understand the end of the string. When we use strPtr, how can we understand the end of the string?

share|improve this question
2  
1) *(strPtr+4) will give you the char i. 2) strPtr is also pointing to status so it'll have the (same) null character (\0) at the end. –  Blue Moon 16 hours ago
2  
Because arrays decays to pointers to their first elements, arrays and pointers can often be used interchangeably, so using the dereference operator on an array will work, as will using the array-indexing operator on a pointer. Also, *(arrayOrPointer + X) is equivalent to arrayOrPointer[X]. –  Joachim Pileborg 16 hours ago
    

5 Answers 5

up vote 11 down vote accepted
char *strPtr;
strPtr = status;

Now your pointer strPtr is pointing to the first character in the array and you can do

int i =0;
while( strPtr[i] != '\0')
{
  printf("%c ",strPtr[i]);
  i++;
}

*strPtr is called dereferencing the pointer to get the value stored in the location the pointer is pointing to.

Make a note that

strPtr[4] = *(strPtr +4); 

Both will get you the value stored at the index 4 of the array.

Note the difference between a pointer and a array name:

----------------------------------
| s  | t  | r  | i  | n | g | \0 |
----------------------------------
  |
strPtr
status

strPtr ++ will make your pointer point to the next element in the array.

| s  | t  | r  | i  | n | g | \0 |
----------------------------------
       |
      strPtr

Whereas you can't do this for the array name

status++ is not allowed because an array is not a modifiable lvalue.

share|improve this answer
    
Wow! that means we can use pointer name- strPtr as an array? I will try it now. Thanks for your reply. –  KajolK 16 hours ago
    
@KajolK Check the edits to get the difference between an array and a pointer –  Gopi 16 hours ago
    
In C, an array index is just a dereference of a pointer after addition: x[i] just means *(x + i). –  Mark Cidade 11 hours ago
1  
@KajolK; Always remember pointers are not arrays and vice-versa. –  haccks 5 hours ago
    
@KajolK: No, it means that the indexing operator [] requires a pointer, not an array, as one of its operands. Often that pointer will be the result of the implicit conversion of an array name. –  Keith Thompson 4 hours ago

Good to know:

char status[10] = "Married";

is just syntax sugar for the equivalent:

char status[10]; // allocate 10 Bytes on stack
status[0] = 'M';
status[1] = 'a';
...
status[6]= 'd';
status[7] = '\0'; // same as 0

Nothing more, nothing less.

Also:

char c = status[3];

is exactly the same as

char c = *(status+3);
share|improve this answer
    
Except new doesn't allocate memory dynamically here, so it should be new (some address in .data or .rodata) char[10]; –  myaut 16 hours ago
1  
I am not sure, is there any 'new' keyword in c? Or should I have to use C++ for this? –  KajolK 16 hours ago
    
@KajolK: There's now new in C. If you want to allocate string dynamically you need malloc(). –  che 16 hours ago
    
well, I've done too much C#. Edited my answer. Thanks. –  DrKoch 16 hours ago
1  
@che There's no new in C. * (I spent far too long looking for the version of C with a new keyword…) –  Blacklight Shining 10 hours ago

The expression status[10] is mere syntactic sugar for *(status+10).

The \0 termination is used under the hood to check for the end, if you were implementing some string-handler yourself you could do this too, or you could ignore it and use some other parameter size given with the string, or you could (don't!) choose anything else as the termination symbol.

This isn't just true of char arrays, or 'strings', a C array is just a pointer to a contiguous block of like-typed stuff with a compile-time check that your 'array' subscripts don't go beyond the 'end' specified at time of declaration. With the *(array+offset) notation, you need to check this for yourself.

share|improve this answer
    
@MattMcNabb Right, that was a stupid edit, not sure what I was thinking there. Re. your first point though, that's why my examples aren't declarations (no type), and I sort of covered the point of the [] declaration with the compile-time check. I will edit to clarify that I am talking about expressions though. Thanks. –  Ollie Ford 12 hours ago
    
@MattMcNabb status[10] is not undefined behavior here; the standard defines dereferencing one past the last element of the array. –  Blacklight Shining 11 hours ago
    
@BlacklightShining it only defines that if there is guaranteed to be allocated memory at that location (and some other conditions are true), which is not the case with char status[10]; –  Matt McNabb 6 hours ago

To get character at index 4 strPtr, you just use strPtr[4] (this also work for status).

To get the end of the string when using strPtr, you need to go through the characters and look for the terminating \0. This is what printf("%s", strPtr) does when it prints the string (and also when it parses the "%s" expression, which is just another string). To find a number of valid characters in the string in C, you use strlen() function. Oh, and make sure you dont do something like this:

char a[3];
strcpy(a, "Hello!");

As this will write 7 bytes into a three-byte memory space, and hence overwrite something you don't want overwritten.

share|improve this answer

The '\0' at the end of the string is a useless add-on designed for easy or safety. You can tell string last character by using 'sizeof' like this:

char status[] = "Married"; 

size_t szLastCharstatus = sizeof(status) / sizeof(status[0]) - 2;

char chLastChar = status[szLastCharstatus];

Detailed explanation:

sizeof(status)

Returns the number of bytes array occpuies.

sizeof(status[0])

Returns the number of bytes first element occupies (and so the rest).

The division between those 2 values gives us the number of elements in the array. To access the last element now we need to subtract one 2 times because elements in array count from zero and because the last character in the string is '\0'.

Also note that arrays are not pointers and vice-versa. Arrays have an implicit conversion to pointer of their first element, constant size and their own type. They can be passed around by pointers or by value (using structure hack is required for the second).

Note that I'm using 'size_t' which is a type-def of a variable storing some size of data.

share|improve this answer
    
That will give the number of element in the array, but not the length of the string contained in the array. Since only 8 characters are initialized, the last two will have indeterminate values and reading them will lead to undefined behavior. Also note that this only works on "proper" arrays, once an array has decayed to a pointer the sizeof trick will no longer work. And the terminator character is not useless, all the standard C string functions rely on it being there. –  Joachim Pileborg 16 hours ago
1  
Also note that the question is tagged C, so no std namespace. –  Joachim Pileborg 16 hours ago
    
@Joachim Pileborg However it's a performance cost sometimes and avoiding it requires complex syntax. The trick will work as long as arrays are passed either by value or pointer. Also fixed for 'C'. –  FISOCPP 15 hours ago
    
The trailing nullbyte isn't useless at all—because of pointer decay, it's actually the only way to find the end of the string if it's e.g. passed to a function as an argument. –  Blacklight Shining 10 hours ago

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.