# Determine Palindrome - How does the operator * work?

This program is supposed to take in a three digit number and change it into its palindrome. `123` would become `321`.

The logic is correct, and the program compiles correctly. :) However, the logic of these does not come easily.

My prof explains things with "stack diagrams" and I find them to be helpful. I created this program based off another program because I noticed the similarities between this and a different program I made, but how does the pointing work?

``````#include <stdio.h>

void reverse_number(int in_val, int *out_val) {
int ones, tens, hundreds;

ones = in_val % 10;
tens = (in_val % 100 - ones) / 10;
hundreds = (in_val - (ones + tens)) / 100;

*out_val = (ones * 100) + (tens * 10) + hundreds;
}

int main() {
int in_val;
int out_val;

printf("Give a three digit num to reverse: \n");
scanf("%d", &in_val);

reverse_number(in_val, &out_val);
printf("New number is: %d \n", out_val);

return 0;
}
```
```

Also, I am now beginning to understand how to write programs based on a kind of template with these pointers, and I understand very basically what the star inside a parameter means (declared as a pointer variable).

For example, I know that `m = &q;` gives variable `m` the address of another variable `q` and I know that `m = *g;` would mean that the value at the address `g` would go into `m` but I am really unfamiliar with how these work in the context of a function and a main file.

If someone could lay out the fundamental logic of how it would work (in this program) that would be awesome. As a math major, I can understand the operations of the math and stuff but the pointers have me not confused but it just seems to me that there are ways to do it without needing to deal with the address of a variable, etc.

Well, since you understood `&` and `*` operators perfectly, the rest is very very simple.

Let's say you have:

``````int q;
int *m;
m = &q;
```
```

Then if you say:

``````int *m2;
m2 = m;
```
```

`m2` will contain the same value as `m`, that is, it will have the address of `q`. Therefore, `*m` and `*m2` will give you the same value (which is the value of `q`) (you do understand that `*` is the inverse operator of `&` right? So `*(&q) = q` and `&(*m) = m` (in the later case, `m` needs to be a pointer for `*` to be applicable.))

So, how does this work with functions? Simple! When you pass arguments to functions, you pass them by value. When you pass by pointer, you are actually passing by value, the pointer of the variable.

So let's examine your function call in detail:

``````reverse_number(in_orig, &out_orig);
```
```

I renamed your `in_val` and `out_val` in the main to `in_orig` and `out_orig` so it won't get mixed with those of `reverse_number`.

Now, `&out_orig` is the address of `out_orig`. When passed as arguments, this gets copied into `out_val` argument of `reverse_number`. This is exactly like writing:

``````int *out_val = &out_orig;
```
```

Now, if you had the above line in your `main`, you could just write `*out_val = something;` and it would change `out_orig`, right? Well, since you have the address of `out_orig` in `out_val`, then who cares if `*out_val` is being set in `main` or `reverse_number`?

So you see? When you have a pointer, you can just copy it around, whether by copying it to another variable or passing it as argument of a function (which is basically the same thing), you can still access the same variable it is pointing to. After all, all the copies have the same value: address of `out_orig`. Now if you want to access it in a function or in `main`, it doesn't really matter.

Edit: `*` in pointer definition

`*` can be used to define a pointer too and this has nothing to do with the previous usage of `*` as an operator that gets the value of an address.

This is just definition, so you have to learn it:

If you have a value of type `type` (for example `int`), then the address of that variable (using `operator &`) has type `type *` (in this example `int *`). Since a pointer takes that address, the type of the pointer is `type *`.

On the contrary, if a pointer has type `type *` (for example `int *`), then getting the value where the pointer points to (using `operator *`) has type `type` (in this example `int`).

In summary, you can say something like this:

``````operator &, adds one * to the type of the variable
operator *, removes one * from the type of the expression
```
```

So let's see some examples:

``````int x;
x has type int
&x has type int *

float *y;
y has type float *
&y has type float **
*y has type float

struct Data ***d;
d has type struct Data ***
&d has type struct Data ****
*d has type struct Data **
*(*d) has type struct Data *
*(*(*d)) has type struct Data
```
```

If you noticed, I said that `&` adds one `*` to the type of variable, but `*` removes one `*` from the type of expression. Why is that? Because `&` gives the address of a variable. Of course, because nothing else has an address. For example `a+b` (possibly) doesn't have any address in the memory, and if it does, it's just temporary and useless.

`operator *` however, works on addresses. No matter how you compute the address, `operator *` works on it. Examples:

``````*(0x12345678) -> Note that even if the compiler let's you do this,
your program will most likely crash

*d -> like we saw before

*(d+4) -> This is the same as writing d[4]
And now you know why arrays and pointers are treated as one
```
```

In case of a dynamic 2d array:

``````*(*(d+4)+6) -> This is the same as writing d[4][6]
```
```