Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > function explanation

Reply
Thread Tools

function explanation

 
 
Jarno A Wuolijoki
Guest
Posts: n/a
 
      09-26-2003
On 25 Sep 2003, Peter Nilsson wrote:

> What is difficult to understand about...?
>
> while (*s++ = *t++)
> ;


First, there's an off by one error. Second, it doesn't terminate the
destination string.




 
Reply With Quote
 
 
 
 
goose
Guest
Posts: n/a
 
      09-26-2003
"Thomas Stegen" <(E-Mail Removed)> wrote in message news:<3f6eb34d$(E-Mail Removed)>...
> "Malcolm" <(E-Mail Removed)> wrote in message
> news:bkl25e$acd$(E-Mail Removed)...
> >
> > "dominant" <(E-Mail Removed)> wrote in message
> > >
> > > void test_function(char *s, char *t)
> > > while(*s++=*t++)
> > > ;
> > > }

> > The combination of three quirky C features in one short loop makes this

> code
> > very difficult to read and debug.
> >

>
> Given the fact that it is a well known and accepted idiom
> it is neither hard to read or hard to debug. First time I saw
> it it took me about 1 minute to figure out what this was
> doing.


also, the pattern of "while (*src_ptr++ = *dst_ptr++)" is
fairly common, and I personally find it intuitive these days
when looking at code. it tells you (or rather, it /should/) the
intent of the programmer without needing a single comment.

goose,
 
Reply With Quote
 
 
 
 
CBFalconer
Guest
Posts: n/a
 
      09-26-2003
Jarno A Wuolijoki wrote:
> On 25 Sep 2003, Peter Nilsson wrote:
>
> > What is difficult to understand about...?
> >
> > while (*s++ = *t++)
> > ;

>
> First, there's an off by one error. Second, it doesn't terminate
> the destination string.


No there isn't (an error). Yes it does (terminate). All assuming
the source is a legitimate string and source and destination do
not overlap.

--
Chuck F ((E-Mail Removed)) ((E-Mail Removed))
Available for consulting/temporary embedded and systems.
<http://cbfalconer.home.att.net> USE worldnet address!


 
Reply With Quote
 
Christopher Benson-Manica
Guest
Posts: n/a
 
      09-26-2003
CBFalconer <(E-Mail Removed)> spoke thus:

>> > while (*s++ = *t++)
>> > ;


> No there isn't (an error). Yes it does (terminate). All assuming
> the source is a legitimate string and source and destination do
> not overlap.


And also that s has space for strlen(t)+1 characters.

--
Christopher Benson-Manica | Jumonji giri, for honour.
ataru(at)cyberspace.org |
 
Reply With Quote
 
John Bode
Guest
Posts: n/a
 
      09-26-2003
Jarno A Wuolijoki <(E-Mail Removed)> wrote in message news:<(E-Mail Removed)>...
> On 25 Sep 2003, Peter Nilsson wrote:
>
> > What is difficult to understand about...?
> >
> > while (*s++ = *t++)
> > ;

>
> First, there's an off by one error.


Where?

> Second, it doesn't terminate the destination string.
>
>


Only if the source string isn't terminated, either.
 
Reply With Quote
 
Jarno A Wuolijoki
Guest
Posts: n/a
 
      09-26-2003
On Fri, 26 Sep 2003, CBFalconer wrote:

> > > What is difficult to understand about...?
> > >
> > > while (*s++ = *t++)
> > > ;

> >
> > First, there's an off by one error. Second, it doesn't terminate
> > the destination string.

>
> No there isn't (an error). Yes it does (terminate).


And that's supposed to be easy to understand?


*t++; /* "get()" */
*s++=x; /* "put(x)" */
*s++=*t++; /* "put(get())" */

while (tmp=*t++) *s++=tmp;
/* "as long as we can get data, append it to s" */
*s=0;
/* terminate s; */

while (*t) *s++=*t++;
*s=0;
/* "as long as there's data, copy it." */

while (*s++=*t++) ;
/* "as long as we have copied nonzero data, do nothing. perform extra
copy as a side effect of embedding it in the test" */

(of course if you interpret "*s++=*t++" as a routine which returns 0
when it has finished it makes a whole lot more sense..)

 
Reply With Quote
 
Irrwahn Grausewitz
Guest
Posts: n/a
 
      09-26-2003
Jarno A Wuolijoki <(E-Mail Removed)> wrote:

>On Fri, 26 Sep 2003, CBFalconer wrote:
>
>> > > What is difficult to understand about...?
>> > >
>> > > while (*s++ = *t++)
>> > > ;
>> >
>> > First, there's an off by one error. Second, it doesn't terminate
>> > the destination string.

>>
>> No there isn't (an error). Yes it does (terminate).

>
>And that's supposed to be easy to understand?


Yes.

<SNIP>

Irrwahn
--
ERROR 103: Dead mouse in hard drive.
 
Reply With Quote
 
pete
Guest
Posts: n/a
 
      09-27-2003
CBFalconer wrote:
>
> Jarno A Wuolijoki wrote:
> > On 25 Sep 2003, Peter Nilsson wrote:
> >
> > > What is difficult to understand about...?
> > >
> > > while (*s++ = *t++)
> > > ;

> >
> > First, there's an off by one error. Second, it doesn't terminate
> > the destination string.

>
> No there isn't (an error). Yes it does (terminate). All assuming
> the source is a legitimate string and source and destination do
> not overlap.


It depends on how they overlap.

--
pete
 
Reply With Quote
 
Malcolm
Guest
Posts: n/a
 
      09-28-2003

"Jarno A Wuolijoki" <(E-Mail Removed)> wrote in message
> On Fri, 26 Sep 2003, CBFalconer wrote:
>
> > > > What is difficult to understand about...?
> > > >
> > > > while (*s++ = *t++)
> > > > ;
> > >
> > > First, there's an off by one error. Second, it doesn't terminate
> > > the destination string.

> >
> > No there isn't (an error). Yes it does (terminate).

>
> And that's supposed to be easy to understand?
>

Exactly. We have a construct that is supposedly "easy to understand",
perfectly acceptable, idiomatic C, and first a newbie posts with "what does
this do" and then another poster mistakes it for a bug.

Most of C is basically the same as any other programming language. Someone
who knows another language will easily understand

int x = 0;

he will also quickly get

for(i=0;i<100;i++)

even though ++ is a pure C idiom.

When it comes to pointers, he has some learning to do. He can quickly pick
up that * is the indirection operator. A bit more difficult is that
*ptr++ increments ptr, rather than *ptr, despite the fact that the ++ is
applied last.

However when we come to

while(*s++ = *t++);

it is a bridge too far for our experienced programmer who only knows a bit
of C. Unless you know, it is deeply counter intutive that = in this context
means "assign" rather than "compare". If he's lucky he will remember the
pointer incrementing and dereference rules, but only just, and this will
make him uncomfortable and unfamiliar with the whole expression. Finally,
using a semi-colon to denote an empty loop is also something that has few
parallels in other languages, and looks like a syntax error.

In short, this expression will make the code harder to read and is likely to
cause trouble. Even an experienced C programmer, though he will not
misinterpret it, will probably take longer to read and understand the
expression and verify that it is correct. This is particularly the case if
it is embedded in a list of other expressions which are also
counter-intutive and difficult to understand.


 
Reply With Quote
 
pete
Guest
Posts: n/a
 
      09-29-2003
Malcolm wrote:

> Even an experienced C programmer, though he will not
> misinterpret it, will probably take longer to read and understand the
> expression and verify that it is correct.


"... the idiom should be mastered,
because you will see it frequently in C programs."

Mastering the idiom means, that you will recognize it,
and know at a glance, what it means.

If you have not mastered it, then it may be tough.
But the mastery that particular idiom, is more common than not,
among experienced C programmers.

A few snippets for you:

void copyarray(e_type *s1, e_type *s2, size_t nmemb)
{
while (nmemb--) {
*s1++ = *s2++;
}
}

char *squeeze(char *s1, const char *s2)
{
char const* p2;
char *const p1 = s1;

for (p2 = strtok(s1, s2); p2; p2 = strtok( 0, s2)) {
while (*p2) {
*s1++ = *p2++;
}
}

*s1 = '\0';
return p1;
}

static void merge(e_type *base, e_type *buffer, size_t nmemb)
{
if (nmemb > SMALL_MERGE) {
size_t const half = nmemb / 2;
e_type *const middle = base + half;
e_type *const after_buffer = buffer + half;
e_type *const after_array = base + nmemb;
e_type *mid_ptr = middle;

merge(base, buffer, half);
merge(middle, buffer, nmemb - half);
while (GTE(middle, base) && middle != base) {
++base;
}
buffer = after_buffer;
while (base != mid_ptr) {
*--buffer = *--mid_ptr;
}
mid_ptr = middle;
while (middle != base) {
*base++ = GT(buffer, mid_ptr) ? *mid_ptr++ : *buffer++;
}
while (after_buffer != buffer && after_array != mid_ptr) {
*base++ = GT(buffer, mid_ptr) ? *mid_ptr++ : *buffer++;
}
while (after_buffer != buffer) {
*base++ = *buffer++;
}
} else {
si_sort(base, nmemb);
}
}

--
pete
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
need an explanation on a function decoration Onix C++ 3 04-01-2008 03:20 PM
Simple Explanation to Networking Wirelessly?? Jaxim Wireless Networking 4 08-19-2005 05:04 AM
write a function such that when ever i call this function in some other function .it should give me tha data type and value of calling function parameter komal C++ 6 01-25-2005 11:13 AM
explanation Mariusz VHDL 1 01-13-2004 02:10 AM
Need Explanation Kaladhaur Palaniappa Perl 0 08-07-2003 09:47 AM



Advertisments