0

While passing a character pointer used to reference a string by its address (i.e. directly via its name or &name[0]) the original string must get passed, since we are passing by address.

However, after executing the following code, I got two different values of address for the first element, which, surprisingly, are 2 bytes apart.

Also, modifying the contents of the string in the function, didn't change the content of the array passed, but this is because a new string will have generated a new address, right?

But about the address of the first element being different, how is that possible?

#include<conio.h>
#include<stdio.h>
#include<iostream.h>

void fn(char *arr)
{
    cout<<endl<<&arr;
    arr="hi";
}

void main()
{
    clrscr();
    char *arr="hey";
    cout<<endl<<"main "<<&arr;//the address is different from that in fn
    fn(arr);
    cout<<endl<<arr;
}
johnsyweb
  • 136,902
  • 23
  • 188
  • 247
tina
  • 91
  • 1
  • 8
  • these are two separate pointers pointing to the same address. although the address doesn't change, the function gets a different pointer variable, its address is irrelevant, which is why just assigning a value to it is meaningless. – Not_a_Golfer May 30 '12 at 21:40
  • 2
    Don't use `void main()`: http://www2.research.att.com/~bs/bs_faq2.html#void-main – chris May 30 '12 at 21:41
  • 1
    See http://stackoverflow.com/q/4810664/78845 for arrays (which are not pointers). In this case, however, you should use `std::string`. – johnsyweb May 30 '12 at 21:44
  • 1
    You must be using a really old compiler for this to build? – johnsyweb May 30 '12 at 21:46
  • 2
    @Johnsyweb : Turbo C++ would be my guess. – ildjarn May 30 '12 at 21:49

2 Answers2

4

You are passing a pointer by value, and then comparing the address of the pointer and the copy, which of course differ. If you want to check that they point to the same memory address you can do that:

std::cout << (void*)arr << std::endl;

modifying the contents of the string in the function, didnt change the content of the array passed

You are not modifying the contents of the string, but rather reassigning the copy of the pointer to point to a different string literal. Also note that modifying the pointed memory (the literal) would be undefined behavior.

The only reason that the compiler let the code through (i.e. compiled it) is that there is a backwards compatibility feature that allows you to have a char* that points to the contents of a string a literal (of type const char[]). You should have got a warning and you should avoid doing that.

David Rodríguez - dribeas
  • 204,818
  • 23
  • 294
  • 489
  • thanks for your answer.i was confusing the pointer's address with the address of the location it points to.i checked the passed pointer by typecasting as a void pointer as you have written, and its same in main() as well as the function. and any changes in the array in the function done as arr[2]='a' reflect changes in the original string of main(). but anyway. i guess (void *) was required to clear up my doubt. so thanks. – tina Jun 02 '12 at 11:04
  • @tina: The cast to `void*` is only needed to force a particular overload of `operator<<` that will print the address. If you don't do the cast the compiler will pick up the `const char*` overload and print the contents. Besides that, the fact is that both pointers refer to the same contents, so if they referred to a *mutable* array, changes through one would be visible through the other. Note that if you are still pointing to a string literal (`"hey"`) it is **undefined behavior**, which means that it might seem to work, or don't, or it might crash your application... – David Rodríguez - dribeas Jun 02 '12 at 14:44
0

Just an FYI. I was unable to comment on a similar question about passing character arrays because it was closed as a duplicate, but the issue is fairly important so hopefully you don't mind if i cross-post.

When using strings in a production application you usually go with UTF-8 because it significantly increases the market without a lot of effort.

http://www.joelonsoftware.com/articles/Unicode.html

Most applications also use a string class to encapsulate the characters. Then you can use something like:

void fn(..., const std::string &static_string, ...);

in your header. If you use a library like gettext, your code looks like:

printf(gettext("and suddenly there's one line which is good.."));

where the english strings act as intuitive indices into localization files and you can rapidly and easily switch languages at install or runtime.

If you can't use a class because you're using C then the gettext docs cover this case as well.

James Fremen
  • 2,170
  • 2
  • 20
  • 29