debugging... dereferencing, & etc.

  • Thread starter =?ISO-8859-1?Q?Martin_J=F8rgensen?=
  • Start date
M

Me

Martin said:
And that should be the same as:

void order(char*& pp1, char*& pp2)

This is exactly what is difficult for me to understand... hmmm. I guess
I'll have to spend some time looking at this...

It's simple, just keep in mind that in C++, *every* type is passed by
value (except for arrays but I'd consider that more like automatic
decomposition into pointers):

void foo(int a)
{
++a;
}

int j = 0;
foo(j);
foo(10); // works

after the call to foo, j is still 0.

void foo(int *a)
{
++*a;
}

int j = 0;
foo(&j);
foo(&10); // error

after the call to foo, j is 1.

void foo(int &a)
{
++a;
}

int j = 0;
foo(j);
foo(10); // error

after the call to foo, j is 1.

For the most part, T &var is exactly the same thing as T * const var
(which is one reason why it has to be initialized and can't be
reassigned later) except having a reference type buys you more things
over just having a pointer. One of the major ones is that the null
reference, *(T*)0, is undefined and with all this combined, this is how
C++ gets away with treating the reference as an automatically
dereferenced pointer.

What's really going to bake your noodle is this:

void foo(const int *a)
{
cout << *a;
}

int j = 0;
foo(&a);
foo(&10); // error

void foo(const int &a)
{
cout << a;
}

int j = 0;
foo(j);
foo(10); // ok

What happens here is that the compiler creates a temporary:

const int dummy = 10;
foo(dummy);

It used to work for regular references but it lead to very hard to
detect bugs like this one:

void foo(int &a)
{
++a;
}

float f = 0;
foo(f); // ok in ancient C++

because the compiler would turn this into:

float f = 0;
int dummy = f;
foo(dummy);
// whoops, the temporary gets incremented but not f
 
R

Richard G. Riley

* Martin Jørgensen:

Uh, it's almost an achievement to find a 10 year old version of the FAQ!
I couldn't if I tried. The current FAQ for this group comes on top of
Google's hit list when I type in "C++ FAQ".

In fairness, that depends on the google being used : it varies on
locale from country to country.
Well, the important thing is that you tried. Hopefully, now that I've
given you direct URLs, next time you'll have a better idea how to find
the most relevant passages. And so on, so in a few months, you'll be
helping others here! :)

hear hear
 
D

Daniel T.

Martin Jørgensen said:
Daniel said:
You could do it the way the standard library functions do it:

bool in_order( const char* left, const char* right )
{
return strcmp( left, right ) < 0;
}

void bsort( const char** first, const char** last )
{
while ( first != last ) {
for ( const char** next = first + 1; next != last; ++next ) {
if ( ! in_order( *first, *next ) )
swap( *first, *next );
}
++first;
}
}

Very nice... Is char **first the same as first[0][0] and also the same
as &first? I keep believing that, anyway - don't know why...

I don't know why ether, they're all different types.

Huh? What's that template/typename-line doing?

Baby steps now... You'll get to it.

{
while ( first != last ) {
for ( T next = first + 1; next != last; ++next ) {
if ( ! ordered( *first, *next ) )
swap( *first, *next );
}
++first;
}
}

Which can be called by:

bsort( p_string, p_string + days, &in_order );

and can also be used to sort other types. For example:

int p_ints[days] = { 3, 1, 5, 6, 4, 0, 2 };

bsort( p_ints, p_ints + days, less<int>() );

(std::less<T> is defined in <functional>)

Never heard about that...

Again, you are learning the language from the inside out. There are all
kinds of useful things that your book simply hasn't bothered to tell you
about. Instead your book is teaching you about parts that should only be
for experts. Thus making it much harder on you than it should be. :-(

I didn't learn about iterators yet, although I read something about it
(but didn't understood it)... In a few weeks, I'll probably know what it
means...

It's simple. An iterator is an object that acts in some ways like a
pointer. There are several kinds of iterators, some act more like
pointers than others.

Nice... I'll have to look at this code, once I learn (more) about
iterators which I don't really know anything about now... :-(

Sure you do, a pointer *is* an iterator.
 
D

Daniel T.

Martin Jørgensen said:
Question 97 here: http://www.cs.indiana.edu/~zlu/cpp_faq.html ?

Or here http://public.research.att.com/~bs/bs_faq.html ?

I didn't find any good enough reason for avoiding #define here even
though I tried.

Try here:
I find that criticism to be too hard. It's a thick book consisting of
about 1000 pages with plenty of examples which I like very much... But
now I have it, so I won't throw it out.

Keep in mind, you aren't an expert in the language. The important thing
though is that the book hasn't dissuaded you from continuing to learn.
 
?

=?ISO-8859-1?Q?Martin_J=F8rgensen?=

Alf said:
* Martin Jørgensen:



Uh, it's almost an achievement to find a 10 year old version of the FAQ!
I couldn't if I tried. The current FAQ for this group comes on top of
Google's hit list when I type in "C++ FAQ".

See e.g. <url: http://www.parashift.com/c++-faq-lite/newbie.html#faq-29.7>.

Thanks... I also think my link was in the top... Can't remember what I
searched on, but I wouldn't have clicked on it if it didn't say:
something about "official comp.lang.c++ FAQ"...
Nearly there!

Good.

Just two mouse-clicks away (or was it one mouse-click), you find



Well, the important thing is that you tried. Hopefully, now that I've
given you direct URLs, next time you'll have a better idea how to find
the most relevant passages. And so on, so in a few months, you'll be
helping others here! :)

I hope, although I don't know if I ever get real "professional"...
Depends on if my professor is interested in my programming skills after
this semester and at this moment I think that he thinks I'm doing a fine
job generally (although this is a new language to me).... Now I'm also
doing my bachelor project (thesis) in C but I've seen some c++ code that
we're all interested in at the department... So I think actually he
wants me to continue learning to program more :)

I'm not trying to learn c++ for doing some kind of homework exercise or
anything... I find this modelling of thermal processes interesting (that
is what my bachelor project is about) and there are some freely
available c++ libraries available that I would like to learn to use
later on.......


Best regards / Med venlig hilsen
Martin Jørgensen
 
?

=?ISO-8859-1?Q?Martin_J=F8rgensen?=

Daniel said:
Very nice... Is char **first the same as first[0][0] and also the same
as &first? I keep believing that, anyway - don't know why...


I don't know why ether, they're all different types.

Oh, yeah..... You're right... If we have:

char **first; // "pointer-to-pointer" - to-char... type: ptr.

first[0][0]; // must be of type char and,
// the first element at memory address *(*(first[0]) )
// or something... ? hmm, not sure....
// I read something like that on google (not in my book)

&first // that is the address of first...
// Isn't that type void * ? (read that on google)...
Huh? What's that template/typename-line doing?


Baby steps now... You'll get to it.


{
while ( first != last ) {
for ( T next = first + 1; next != last; ++next ) {
if ( ! ordered( *first, *next ) )
swap( *first, *next );
}
++first;
}
}

Which can be called by:

bsort( p_string, p_string + days, &in_order );

and can also be used to sort other types. For example:

int p_ints[days] = { 3, 1, 5, 6, 4, 0, 2 };

bsort( p_ints, p_ints + days, less<int>() );

(std::less<T> is defined in <functional>)

Never heard about that...


Again, you are learning the language from the inside out. There are all
kinds of useful things that your book simply hasn't bothered to tell you
about. Instead your book is teaching you about parts that should only be
for experts. Thus making it much harder on you than it should be. :-(

Oh... Well, at least I like to learn about pointers, because when you
make functions (which is very likely) and you need to pass variables
then I think it's really important to know what's happening...

So, I'm still struggling a bit with the above but feel comfortable with
only dereferencing a pointer-to-something (one star "*"), as mentioned
earlier...
It's simple. An iterator is an object that acts in some ways like a
pointer. There are several kinds of iterators, some act more like
pointers than others.

Oh, perhaps I should take a closer look at that in my book somewhere in
the weekend...
Sure you do, a pointer *is* an iterator.

Ok... Then I must try it out soon :)


Best regards / Med venlig hilsen
Martin Jørgensen
 
?

=?ISO-8859-1?Q?Martin_J=F8rgensen?=

Me said:
It's simple, just keep in mind that in C++, *every* type is passed by
value (except for arrays but I'd consider that more like automatic
decomposition into pointers):

Oh..... Thanks for telling that inside the paranthesis... I just want to
make sure I understand that, so I've made some example code (untested)...

int n[5] = { {0,1,2,3,4} }; // untested - perhaps syntax error here?
int * ptr; // declaration
ptr = n[0]; // ptr points to first integer value now

// method 1.
function(ptr) // is this like passing &ptr? I think it is?...

// method 2.
function(n[0]) // is this like passing &n[0] or???


If somebody has comments, I'm sure I will think about that next time
I'll have time to debug some more and watch what is going on with some
example programs that is passing values and references on to functions...


-snip-


Best regards / Med venlig hilsen
Martin Jørgensen
 
M

Me

Martin said:
int n[5] = { {0,1,2,3,4} }; // untested - perhaps syntax error here?

Some compilers accept extra braces but it's non-standard. It should be:

int n[5] = { 0, 1, 2, 3, 4 };
int * ptr; // declaration

and definition
ptr = n[0]; // ptr points to first integer value now

The type of n is int[5], the type of ptr is int *, the type of n[0] is
int. You need to apply the & operator to the int expression to convert
it to int *.
// method 1.
function(ptr) // is this like passing &ptr? I think it is?...

The type of ptr is int *. The type of &ptr is int **. It would be like
passing &ptr if function was declared like:

ret function(int *&);
instead of:
ret function(int *);
// method 2.
function(n[0]) // is this like passing &n[0] or???

The type of n[0] is int. The type of &n[0] is int *. It would be like
passing &n[0] if function was declared like:

ret function(int &);
instead of:
ret function(int);
If somebody has comments, I'm sure I will think about that next time
I'll have time to debug some more and watch what is going on with some
example programs that is passing values and references on to functions...

Arrays automatically decompose into pointers in certain contexts
(^^^^this only applies to the top-level array^^^^). For example:

int a[5] = { 1, 2, 3, 4, 5 };
int *p = &a[0];
/* the compiler internally converts this to: */
int *p = &*((int*)a + 0);
/* which is exactly equivalent to: */
int *p = (int*)a + 0;
/* which can be further optimized to: */
int *p = (int*)a;
/* leading us to just simply use the following instead: */
int *p = a;

This doesn't occur with this example because it only applies to the
top-level array:

int m[1][1] = { 0 };
int (*q)[1] = a;
/* good, we can convert int[1][1] (an array of an array of ints) to int
(*)[1] (a pointer to an array of ints) */
int **q = m;
/* error, we can't convert int[1][1] to int** (a pointer to a pointer
to an int) */


And just incase you're confused about precedence, &a[0] means &(a[0])
and not (&a)[0]. There is a slight difference:

int a[5];

a[0] is int, &(a[0]) is int *
&a is int(*)[5], (&a)[0] is int[5]

Most of the time it doesn't matter, but it makes the difference with:

void fn(int (&)[5]);

fn(&a[0]); // bad
fn(a); // good
fn((&a)[0]); // good
fn(*&a); /* good, this is the same thing remember? */

See if you can work your way through the types of the expressions to
see why.
 
?

=?ISO-8859-1?Q?Martin_J=F8rgensen?=

Me said:
Martin said:
int n[5] = { {0,1,2,3,4} }; // untested - perhaps syntax error here?


Some compilers accept extra braces but it's non-standard. It should be:

int n[5] = { 0, 1, 2, 3, 4 };
Thanks...
int * ptr; // declaration


and definition

ptr = n[0]; // ptr points to first integer value now


The type of n is int[5], the type of ptr is int *, the type of n[0] is
int. You need to apply the & operator to the int expression to convert
it to int *.

Oh.... Makes sense.
The type of ptr is int *. The type of &ptr is int **. It would be like
passing &ptr if function was declared like:

ret function(int *&);
instead of:
ret function(int *);

hmmm. I see...
// method 2.
function(n[0]) // is this like passing &n[0] or???


The type of n[0] is int. The type of &n[0] is int *. It would be like
passing &n[0] if function was declared like:

ret function(int &);
instead of:
ret function(int);

Okay... I'll have to study this a couple of times more :)
If somebody has comments, I'm sure I will think about that next time
I'll have time to debug some more and watch what is going on with some
example programs that is passing values and references on to functions...


Arrays automatically decompose into pointers in certain contexts
(^^^^this only applies to the top-level array^^^^). For example:

int a[5] = { 1, 2, 3, 4, 5 };
int *p = &a[0];
/* the compiler internally converts this to: */
int *p = &*((int*)a + 0);
/* which is exactly equivalent to: */
int *p = (int*)a + 0;
/* which can be further optimized to: */
int *p = (int*)a;
/* leading us to just simply use the following instead: */
int *p = a;

This doesn't occur with this example because it only applies to the
top-level array:

int m[1][1] = { 0 };
int (*q)[1] = a;
/* good, we can convert int[1][1] (an array of an array of ints) to int
(*)[1] (a pointer to an array of ints) */
int **q = m;
/* error, we can't convert int[1][1] to int** (a pointer to a pointer
to an int) */


And just incase you're confused about precedence, &a[0] means &(a[0])
and not (&a)[0]. There is a slight difference:

int a[5];

a[0] is int, &(a[0]) is int *
&a is int(*)[5], (&a)[0] is int[5]

Most of the time it doesn't matter, but it makes the difference with:

void fn(int (&)[5]);

fn(&a[0]); // bad
fn(a); // good
fn((&a)[0]); // good
fn(*&a); /* good, this is the same thing remember? */

See if you can work your way through the types of the expressions to
see why.

Wow.... I'll have to print this out tomorrow and study it carefully :)

Thanks a lot - looks like some very good comments for me...


Best regards / Med venlig hilsen
Martin Jørgensen
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,995
Messages
2,570,236
Members
46,822
Latest member
israfaceZa

Latest Threads

Top