Pointer arithmetic question.

Discussion in 'C Programming' started by Adrian Sch, Oct 30, 2012.

  1. Adrian Sch

    Adrian Sch Guest

    Hello! I am doing some exercises from K&R 2nd edition and I seem to be stuck: Here's a working copy of a custom strcpy:

    char *strcpy(char * s, char * t)
    {

    char x;
    while(x=*s)
    s++;

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

    return ;
    }
    int main(void)
    {
    char message[100]="string1";
    char * message2="string2";
    strcpy(message, message2);
    printf("%s", message);
    return 0;

    }

    And here's a version that doesn't work:
    char *strcpy(char * s, char * t)
    {

    while(*s++)
    ;

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

    return ;
    }
    int main(void)
    {
    char message[100]="string1";
    char * message2="string2";
    strcpy(message, message2);
    printf("%s", message);
    return 0;

    }
    It seems that for some reason the while(*s++) is 0 so it doesn't increment. Why? What am I missing here?
     
    Adrian Sch, Oct 30, 2012
    #1
    1. Advertising

  2. Adrian Sch

    tom st denis Guest

    On Oct 30, 1:33 pm, Adrian Sch <> wrote:
    > Hello! I am doing some exercises from K&R 2nd edition and I seem to be stuck: Here's a working copy of a custom strcpy:
    >
    > char *strcpy(char * s, char * t)
    > {
    >
    > char x;
    > while(x=*s)
    > s++;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;}
    >
    > int main(void)
    > {
    > char message[100]="string1";
    > char * message2="string2";
    > strcpy(message, message2);
    > printf("%s", message);
    > return 0;
    >
    > }
    >
    > And here's a version that doesn't work:
    > char *strcpy(char * s, char * t)
    > {
    >
    > while(*s++)
    > ;


    Ask your self, where does "s" point now. (hint: compare the value of
    's' in this version against the other via printf("%p\n", s)).

    > while((*s++=*t++))
    > ;
    >
    > return ;}
    >
    > int main(void)
    > {
    > char message[100]="string1";
    > char * message2="string2";
    > strcpy(message, message2);
    > printf("%s", message);
    > return 0;
    >
    > }
    >
    > It seems that for some reason the while(*s++) is 0 so it doesn't increment. Why? What am I missing here?


    Once you figure out where 's' points to after the while(*s++) loop
    you'll figure out the bug in the 2nd copy.

    Tom
     
    tom st denis, Oct 30, 2012
    #2
    1. Advertising

  3. Adrian Sch

    Greg Martin Guest

    On 12-10-30 10:33 AM, Adrian Sch wrote:
    > Hello! I am doing some exercises from K&R 2nd edition and I seem to be stuck: Here's a working copy of a custom strcpy:
    >
    > char *strcpy(char * s, char * t)
    > {
    >
    > char x;
    > while(x=*s)
    > s++;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;
    > }
    > int main(void)
    > {
    > char message[100]="string1";
    > char * message2="string2";
    > strcpy(message, message2);
    > printf("%s", message);
    > return 0;
    >
    > }
    >
    > And here's a version that doesn't work:
    > char *strcpy(char * s, char * t)
    > {
    >
    > while(*s++)
    > ;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;
    > }
    > int main(void)
    > {
    > char message[100]="string1";
    > char * message2="string2";
    > strcpy(message, message2);
    > printf("%s", message);
    > return 0;
    >
    > }
    > It seems that for some reason the while(*s++) is 0 so it doesn't increment. Why? What am I missing here?
    >


    I made a couple of changes to your program. Some to make my compiler
    happy, some for readability and one to make the program work. The
    pre-increment will return the value after incrementing where as the
    post-increment returns it then increments the value. In your version you
    begin the to write after the NIL, in mine I overwrite it.

    #include <stdio.h>

    char* strcpy(char* s, char* t) {
    while(*++s);

    while((*s++=*t++) != '\0');

    return s;
    }

    int main(void) {
    char message[100]="string1";
    char* message2="string2";

    strcpy(message, message2);
    printf("%s\n", message);

    return 0;
    }
     
    Greg Martin, Oct 30, 2012
    #3
  4. Adrian Sch

    BartC Guest

    "Adrian Sch" <> wrote in message
    news:...
    > Hello! I am doing some exercises from K&R 2nd edition and I seem to be
    > stuck: Here's a working copy of a custom strcpy:
    >
    > char *strcpy(char * s, char * t)
    > {
    >
    > char x;
    > while(x=*s)
    > s++;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;
    > }


    Do you mean strcat rather than strcpy?

    --
    Bartc
     
    BartC, Oct 30, 2012
    #4
  5. Adrian Sch <> writes:

    > Hello! I am doing some exercises from K&R 2nd edition and I seem to be
    > stuck: Here's a working copy of a custom strcpy:


    No, it's a not-quite working version on strcat.

    > char *strcpy(char * s, char * t)
    > {
    >
    > char x;
    > while(x=*s)
    > s++;


    What is x for? You never use it.

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


    You compiler should have complained to you about this. Adjust the
    warning level to the highest you can. There's no reason not to get the
    maximum help you can.

    > }
    > int main(void)
    > {
    > char message[100]="string1";
    > char * message2="string2";
    > strcpy(message, message2);
    > printf("%s", message);
    > return 0;
    >
    > }


    Also, get into the habit of layingout your code using some standard or
    other. I know that the above layout could have been due to Google's
    awful Usenet interface, but some of it is yours. Pick a style and stick
    to it.

    > And here's a version that doesn't work:
    > char *strcpy(char * s, char * t)
    > {
    >
    > while(*s++)
    > ;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;
    > }
    > int main(void)
    > {
    > char message[100]="string1";
    > char * message2="string2";
    > strcpy(message, message2);
    > printf("%s", message);
    > return 0;
    >
    > }
    > It seems that for some reason the while(*s++) is 0


    That makes not sense. A while loop always ends when it's condition is
    zero. That's as true of the working as of the the non-working version.

    > so it doesn't increment. Why? What am I missing here?


    Play computer: draw a string and a pointer to it, then step through what
    this loop does until you see what's wrong. I'll gladly tell you, but
    you'll learn more by stepping through it yourself:

    +------------+
    s: | o |
    +-----+------+
    |
    V
    +-----+-----+-----+-----+-----+-----+-----+-----+
    | s | t | r | i | n | g | 1 | \0 |
    +-----+-----+-----+-----+-----+-----+-----+-----+

    (you'll need a fixed-width font to see this.)

    --
    Ben.
     
    Ben Bacarisse, Oct 30, 2012
    #5
  6. Adrian Sch

    James Kuyper Guest

    On 10/30/2012 01:33 PM, Adrian Sch wrote:
    > Hello! I am doing some exercises from K&R 2nd edition and I seem to be stuck: Here's a working copy of a custom strcpy:
    >
    > char *strcpy(char * s, char * t)
    > {
    >
    > char x;
    > while(x=*s)
    > s++;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;
    > }
    > int main(void)
    > {
    > char message[100]="string1";
    > char * message2="string2";
    > strcpy(message, message2);
    > printf("%s", message);
    > return 0;
    >
    > }
    >
    > And here's a version that doesn't work:
    > char *strcpy(char * s, char * t)
    > {
    >
    > while(*s++)
    > ;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;
    > }
    > int main(void)
    > {
    > char message[100]="string1";
    > char * message2="string2";
    > strcpy(message, message2);
    > printf("%s", message);
    > return 0;
    >
    > }
    > It seems that for some reason the while(*s++) is 0 so it doesn't increment. Why? What am I missing here?


    The 'x' is irrelevant. You may find it easier to understand what's going
    on if you remove it. Your working version had the equivalent of:

    while(*s) s++;

    The version that didn't work had the equivalent of:

    while(*s++);

    When s points at "string1", how many times does s++ get executed with
    the working version of the code? How many times with the version that
    failed? In each case, where does s point after the loop is finished
    executing?
    --
    James Kuyper
     
    James Kuyper, Oct 30, 2012
    #6
  7. Adrian Sch

    Eric Sosman Guest

    On 10/30/2012 1:33 PM, Adrian Sch wrote:
    > Hello! I am doing some exercises from K&R 2nd edition and I seem to be stuck: Here's a working copy of a custom strcpy:
    >
    > char *strcpy(char * s, char * t)
    > {
    >
    > char x;
    > while(x=*s)
    > s++;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;
    > }


    That's not a strcpy() work-alike. Looks more like strcat(),
    which is a different breed of, well, cat.

    > And here's a version that doesn't work:
    > char *strcpy(char * s, char * t)
    > {
    >
    > while(*s++)
    > ;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;
    > }


    This isn't a work-alike for any of the standard string
    functions, and certainly not for strcpy() or strcat(). A name
    like strabut() might describe what it does, which is: "Copy the
    `t' string to the memory area just after the `s' string, leaving
    the '\0' at the end of `s' undisturbed."

    I think what you've overlooked is that the test in the first
    `while' loop will detect the '\0' character *and* will advance
    `s' past that character. If you want to append the `t' characters
    to `s', you should deposit the first of them right where the '\0'
    was originally; as things stand, you're depositing that first
    character just after the '\0'.

    --
    Eric Sosman
    d
     
    Eric Sosman, Oct 30, 2012
    #7
  8. Adrian Sch

    Eric Sosman Guest

    On 10/30/2012 2:00 PM, Greg Martin wrote:
    > [...]
    > I made a couple of changes to your program. Some to make my compiler
    > happy, some for readability and one to make the program work. The
    > pre-increment will return the value after incrementing where as the
    > post-increment returns it then increments the value. In your version you
    > begin the to write after the NIL, in mine I overwrite it.
    >
    > #include <stdio.h>
    >
    > char* strcpy(char* s, char* t) {
    > while(*++s);


    This fails if `s' points to an empty string: It skips right
    over the '\0' at the beginning and starts exploring the trackless
    wilderness after the terminator. (It's very bad to find yourself
    on the wrong side of The Terminator -- just ask Ahhnold.)

    --
    Eric Sosman
    d
     
    Eric Sosman, Oct 30, 2012
    #8
  9. Adrian Sch

    Greg Martin Guest

    On 12-10-30 12:17 PM, Eric Sosman wrote:
    > On 10/30/2012 2:00 PM, Greg Martin wrote:
    >> [...]
    >> I made a couple of changes to your program. Some to make my compiler
    >> happy, some for readability and one to make the program work. The
    >> pre-increment will return the value after incrementing where as the
    >> post-increment returns it then increments the value. In your version you
    >> begin the to write after the NIL, in mine I overwrite it.
    >>
    >> #include <stdio.h>
    >>
    >> char* strcpy(char* s, char* t) {
    >> while(*++s);

    >
    > This fails if `s' points to an empty string: It skips right
    > over the '\0' at the beginning and starts exploring the trackless
    > wilderness after the terminator. (It's very bad to find yourself
    > on the wrong side of The Terminator -- just ask Ahhnold.)
    >


    Very true. Thanks Eric. There's a reason I hate those little shortcuts!
     
    Greg Martin, Oct 30, 2012
    #9
  10. Adrian Sch

    Adrian Sch Guest

    marți, 30 octombrie 2012, 20:00:49 UTC+2, Greg Martin a scris:
    > On 12-10-30 10:33 AM, Adrian Sch wrote:
    >
    > > Hello! I am doing some exercises from K&R 2nd edition and I seem to be stuck: Here's a working copy of a custom strcpy:

    >
    > >

    >
    > > char *strcpy(char * s, char * t)

    >
    > > {

    >
    > >

    >
    > > char x;

    >
    > > while(x=*s)

    >
    > > s++;

    >
    > >

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

    >
    > > ;

    >
    > >

    >
    > > return ;

    >
    > > }

    >
    > > int main(void)

    >
    > > {

    >
    > > char message[100]="string1";

    >
    > > char * message2="string2";

    >
    > > strcpy(message, message2);

    >
    > > printf("%s", message);

    >
    > > return 0;

    >
    > >

    >
    > > }

    >
    > >

    >
    > > And here's a version that doesn't work:

    >
    > > char *strcpy(char * s, char * t)

    >
    > > {

    >
    > >

    >
    > > while(*s++)

    >
    > > ;

    >
    > >

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

    >
    > > ;

    >
    > >

    >
    > > return ;

    >
    > > }

    >
    > > int main(void)

    >
    > > {

    >
    > > char message[100]="string1";

    >
    > > char * message2="string2";

    >
    > > strcpy(message, message2);

    >
    > > printf("%s", message);

    >
    > > return 0;

    >
    > >

    >
    > > }

    >
    > > It seems that for some reason the while(*s++) is 0 so it doesn't increment. Why? What am I missing here?

    >
    > >

    >
    >
    >
    > I made a couple of changes to your program. Some to make my compiler
    >
    > happy, some for readability and one to make the program work. The
    >
    > pre-increment will return the value after incrementing where as the
    >
    > post-increment returns it then increments the value. In your version you
    >
    > begin the to write after the NIL, in mine I overwrite it.
    >
    >
    >
    > #include <stdio.h>
    >
    >
    >
    > char* strcpy(char* s, char* t) {
    >
    > while(*++s);
    >
    >
    >
    > while((*s++=*t++) != '\0');
    >
    >
    >
    > return s;
    >
    > }
    >
    >
    >
    > int main(void) {
    >
    > char message[100]="string1";
    >
    > char* message2="string2";
    >
    >
    >
    > strcpy(message, message2);
    >
    > printf("%s\n", message);
    >
    >
    >
    > return 0;
    >
    > }


    First, thanks to all of you for the replies.

    Second, you are right, this a not-working strcat version.

    Third, this is a very subtle problem and quite hard to identify consideringmy limited knowledge. Because my real question was why the "while(*s++);" gets skiped in the code. Because I was using a debuger and I was expecting some additional action. But because there was no block of code to execute and go back again to the while test, the while test was executed at once (very fast). Am I right or wrong? Because that seemed stupid to me, how the while get skipped while *s was pointing to s.
    Now for the real question, that I didn't ask. I figured that the subtlety of the postfix increment is causing my trouble. Because once the *s is pointing at null, it is incremented one more time and the future copies of *t value go after the null. So when I am printing message, I have concatenated the string, but unfortunately after the null, and that makes it just (not random) garbage as far as printf is concerned.
    I used a quick hack to fix it: using the prefix operator. That worked! But I think that this is wrong because if the first string's first character was null,then I'd repeat the whole affair from before and have concatenated the string after the null.

    Forth, here's the fix(as sugested by some of you):
    char *strcpy(char * s, char * t)
    {

    while(*s)
    s++;

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

    return ;
    }

    Fifth, Is there any other way to keep simple and elegant, but on just one line of code? Or maybe a messier way, but also to fit in the while testing block? I am thinking and if else shortcut notation, but I don't master the idiom that well to do this apparently.
     
    Adrian Sch, Oct 30, 2012
    #10
  11. Adrian Sch <> writes:
    > Hello! I am doing some exercises from K&R 2nd edition and I seem to be
    > stuck: Here's a working copy of a custom strcpy:
    >
    > char *strcpy(char * s, char * t)
    > {
    >
    > char x;
    > while(x=*s)
    > s++;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;
    > }
    > int main(void)
    > {
    > char message[100]="string1";
    > char * message2="string2";
    > strcpy(message, message2);
    > printf("%s", message);
    > return 0;
    >
    > }

    [...]

    As several other people have pointed out, that's an implementation of
    strcat, not of strcpy.

    Here's a reformatted version:

    char *strcpy(char *s, char *t)
    {
    char x;
    while(x = *s)
    s++;

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

    int main(void)
    {
    char message[100] = "string1";
    char *message2 = "string2";
    strcpy(message, message2);
    puts(message);
    return 0;
    }

    I've fixed the indentation and added consistent whitespace in
    some places. I've also changed your printf() call to puts(),
    so that it prints a newline after the message.

    Some remarks, in addition to what others have said:

    You need to add "#include <stdio.h>" if you're going to call either
    printf or puts.

    The names "strcpy" and "strcat" are reserved, as are all identifiers
    starting with "str" (or "mem", or "wcs") and a lowercase letter.
    Which means that, unless you're actually implementing the C standard
    library, you shouldn't call your own function "strcpy" or "strcat".
    You could call it "str_cat", for example, or "my_strcat".

    --
    Keith Thompson (The_Other_Keith) <http://www.ghoti.net/~kst>
    Will write code for food.
    "We must do something. This is something. Therefore, we must do this."
    -- Antony Jay and Jonathan Lynn, "Yes Minister"
     
    Keith Thompson, Oct 30, 2012
    #11
  12. Adrian Sch

    Eric Sosman Guest

    On 10/30/2012 3:50 PM, Adrian Sch wrote:
    > [...]
    > Forth, here's the fix(as sugested by some of you):
    > char *strcpy(char * s, char * t)
    > {
    >
    > while(*s)
    > s++;
    >
    > while((*s++=*t++))
    > ;
    >
    > return ;


    Looks like you didn't read Ben Bacarisse's response.

    > }
    >
    > Fifth, Is there any other way to keep simple and elegant, but on just one line of code? Or maybe a messier way, but also to fit in the while testing block? I am thinking and if else shortcut notation, but I don't master the idiom that well to do this apparently.


    Yes! The one line you need is

    #include <string.h>

    That is, in real programs you should use the library's functions
    instead of writing your own replacements. But this isn't a "real
    program;" it's a learning exercise. So, as a learning challenge:
    Can you get the whole thing on one line?

    If your screen is wide enough, the answer, again, is Yes!

    char*mystrcpy(char*s,char*t){while(*s)s++;while(*s++=*t++);return/*wrong!*/;}

    Okay, okay, so how about "one loop" instead of "one line?"

    Once again, Yes!

    char *mystrcpy(char *s, char *t) {
    for (s += strlen(s); *s++ = *t++; );
    return /*wrong*/ ;
    }

    But if you don't want to use existing library functions then I
    think the answer is No. You need to do two distinct things: Find
    the end of the `s' string, and copy the `t' characters to it. It's
    *possible* to combine those two operations into one loop, but I can
    think of no way that could be called "elegant" or "simple."

    --
    Eric Sosman
    d
     
    Eric Sosman, Oct 30, 2012
    #12
  13. Adrian Sch

    Adrian Sch Guest

    > On 10/30/2012 3:50 PM, Adrian Sch wrote:
    >
    >> [...]
    >> Forth, here's the fix(as sugested by some of you):
    >> char *strcpy(char * s, char * t)
    >> {
    >> while(*s)
    >> s++;
    >> while((*s++=*t++))
    >> ;
    >> return ;
    >>

    > Looks like you didn't read Ben Bacarisse's response.
    >

    I did read it. If you are referring to code formatting then know that I am formatting my code, but it just how it looks when I paste it here.
     
    Adrian Sch, Oct 30, 2012
    #13
  14. Adrian Sch

    Adrian Sch Guest


    > Can you get the whole thing on one line?
    >
    >
    >
    > If your screen is wide enough, the answer, again, is Yes!
    >
    >
    >
    > char*mystrcpy(char*s,char*t){while(*s)s++;while(*s++=*t++);return/*wrong!*/;}
    >
    >

    This is kind of obvious, and is not what I was having in mind, but thanks for the tip anyway:D



    >
    > Okay, okay, so how about "one loop" instead of "one line?"
    >
    >
    >
    > Once again, Yes!
    >
    >
    >
    > char *mystrcpy(char *s, char *t) {
    >
    > for (s += strlen(s); *s++ = *t++; );
    >
    > return /*wrong*/ ;
    >
    > }
    >

    This is interesting!

    >
    >
    > But if you don't want to use existing library functions then I
    >
    > think the answer is No. You need to do two distinct things: Find
    >
    > the end of the `s' string, and copy the `t' characters to it. It's
    >
    > *possible* to combine those two operations into one loop, but I can
    >
    > think of no way that could be called "elegant" or "simple."
    >
    >
    >
    > --
    >
    > Eric Sosman
    >
    > d


    So there's no way to translate
    while(*s)
    s++;

    into something like (pseudocode)
    while(*s?s++:break)
    the code above doesn't compile. Why is not possible to cram a if statement into a while testing block? Stupid question probably, but that's my way of learning.
     
    Adrian Sch, Oct 30, 2012
    #14
  15. Adrian Sch <> writes:

    >> On 10/30/2012 3:50 PM, Adrian Sch wrote:
    >>
    >>> [...]
    >>> Forth, here's the fix(as sugested by some of you):
    >>> char *strcpy(char * s, char * t)
    >>> {
    >>> while(*s)
    >>> s++;
    >>> while((*s++=*t++))
    >>> ;
    >>> return ;
    >>>

    >> Looks like you didn't read Ben Bacarisse's response.
    >>

    > I did read it. If you are referring to code formatting then know that
    > I am formatting my code, but it just how it looks when I paste it
    > here.


    Eric is referring to the missing expression in the return statement and,
    possibly, my associated comments about getting your compiler to tell you
    as much as you can get it to. You shouldn't pass up the chance to get a
    helping hand from the compiler. By default, I compile with as many
    warnings turned on as I can.

    Some warnings you will then ignore, but you'll learn from finding out
    why you can ignore a particular warning in a particular situation.

    --
    Ben.
     
    Ben Bacarisse, Oct 30, 2012
    #15
  16. Adrian Sch <> writes:
    <snip>
    > So there's no way to translate
    > while(*s)
    > s++;


    (I've fixed the indentation -- it's so important in fragments like this)

    > into something like (pseudocode)
    > while(*s?s++:break)


    Yes. Borrowing your conditional expression, you can write

    while (*s ? s++ : 0);

    but

    while (*s && s++);

    is simpler. However, the original is simpler still so there is nothing
    at all to be gained.

    You could also stick with while (*s++); and compensate for being one
    place ahead of yourself later, but that works out (in that case) to be
    even worse.

    > the code above doesn't compile. Why is not possible to cram a if
    > statement into a while testing block? Stupid question probably, but
    > that's my way of learning.


    It's fun to try these things out but they are often worse than you
    imagine. For one thing, simpler can often be harder to read, and most
    code is read far more often that it's written (and frequently by people
    who have no idea what on earth you were thinking when you wrote it).

    But, as I said, it can be fun. I just wasted a few minutes writing both
    loops as one, but I didn't post it because the results were, as
    expected, awful. I came up with:

    while (*s || *t)
    if (*s) s++;
    else *s++ = *t++, *s = 0;

    and

    while (*s || *t)
    if (!*s++) s[-1] = *t++, *s = 0;

    and even (with it all in the condition of the loop):

    char *r = 0;
    while (*s++ || !r && (r = s - 1) || (*r++ = *t++));

    (In my defence, I never though it would be worth the attempt -- the
    desire to tinker simply got the better of me.)

    --
    Ben.
     
    Ben Bacarisse, Oct 30, 2012
    #16
  17. Adrian Sch

    James Kuyper Guest

    On 10/30/2012 06:45 PM, Adrian Sch wrote:
    >
    >> Can you get the whole thing on one line?

    ....
    >> But if you don't want to use existing library functions then I
    >> think the answer is No. You need to do two distinct things: Find
    >> the end of the `s' string, and copy the `t' characters to it. It's
    >> *possible* to combine those two operations into one loop, but I can
    >> think of no way that could be called "elegant" or "simple."

    ....
    > So there's no way to translate
    > while(*s)
    > s++;


    When you talked about "just one line of code", Eric apparently assumed
    (as did I) that you were referring to the entire function. It's not
    possible to make that code any simpler or more elegant, as you
    requested, but it is trivial to turn it into a one-liner:

    while(*s) s++;

    > into something like (pseudocode)
    > while(*s?s++:break)
    > the code above doesn't compile. Why is not possible to cram a if statement into a while testing block? Stupid question probably, but that's my way of learning.


    The problem with that piece of code is that while statements can contain
    expressions, expressions can never contain statements.
    The third operand of the ?: operator is required to be a conditional
    expression. The "break" keyword isn't any kind of an expression, it's
    only permitted use is as part of a break statement. Break statements are
    only allowed inside the body of a while() loop or a switch statement.
    You're trying to use it in the controlling condition, which is required
    to be an expression; it's not part of the loop body.

    The expression 0 would be perfectly acceptable in this context, and
    would have the same effect you're trying to achieve by using "break":

    while(*s?s++:0);

    You could also use

    while(*s && s++);

    but both of those are unnecessarily "clever", and I don't mean that as a
    compliment. If I made a mistake in writing them down (which is quite
    possible), that would demonstrate why such "cleverness" is a bad idea. I
    don't think that either of those statements is any kind of improvement over

    while(*s) s++;
    --
    James Kuyper
     
    James Kuyper, Oct 30, 2012
    #17
  18. Adrian Sch

    Greg Martin Guest

    On 12-10-30 04:20 PM, Ben Bacarisse wrote:

    >
    > while (*s || *t)
    > if (*s) s++;
    > else *s++ = *t++, *s = 0;
    >
    > and
    >
    > while (*s || *t)
    > if (!*s++) s[-1] = *t++, *s = 0;
    >
    > and even (with it all in the condition of the loop):
    >
    > char *r = 0;
    > while (*s++ || !r && (r = s - 1) || (*r++ = *t++));
    >
    > (In my defence, I never though it would be worth the attempt -- the
    > desire to tinker simply got the better of me.)
    >


    That kind of thinking can lead to no good. :)
    http://www.ioccc.org/2012/blakely/blakely.c
     
    Greg Martin, Oct 31, 2012
    #18
  19. Adrian Sch

    Eric Sosman Guest

    On 10/30/2012 6:34 PM, Adrian Sch wrote:
    >> On 10/30/2012 3:50 PM, Adrian Sch wrote:
    >>
    >>> [...]
    >>> Forth, here's the fix(as sugested by some of you):
    >>> char *strcpy(char * s, char * t)
    >>> {
    >>> while(*s)
    >>> s++;
    >>> while((*s++=*t++))
    >>> ;
    >>> return ;
    >>>

    >> Looks like you didn't read Ben Bacarisse's response.
    >>

    > I did read it. If you are referring to code formatting then know that I am formatting my code, but it just how it looks when I paste it here.


    Perhaps you should pay attention to other things Ben wrote,
    referring to places I highlighted with /*wrong*/ comments...

    (Kudos to Ben, by the way: On first reading, I completely
    missed the problem he pointed out.)

    --
    Eric Sosman
    d
     
    Eric Sosman, Oct 31, 2012
    #19
  20. Adrian Sch

    S R Guest

    On Oct 31, 4:20 am, Ben Bacarisse <> wrote:

    [snip]

    >
    >      char *r = 0;
    >      while (*s++ || !r && (r = s - 1) || (*r++ = *t++));

    ^^^^^
    I think there is a problem with the above. Once we reach the end of
    string s, s is not guaranteed to point to a location containing 0 as
    its value, assuming s as being sent in by the caller of the function
    (in your earlier examples you made ",*s =0" which was the correct).
    The concatenation happens through r but the check *s++ is problematic,
    isn't it?

    Cheers,

    --
    SR
     
    S R, Nov 2, 2012
    #20
    1. Advertising

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

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. joshc
    Replies:
    5
    Views:
    559
    Keith Thompson
    Mar 31, 2005
  2. Kenneth Brody

    Pointer arithmetic question

    Kenneth Brody, Jan 20, 2006, in forum: C Programming
    Replies:
    23
    Views:
    1,554
    Keith Thompson
    Jan 23, 2006
  3. , India

    beginner's question on pointer arithmetic

    , India, Mar 12, 2007, in forum: C Programming
    Replies:
    8
    Views:
    345
    santosh
    Mar 12, 2007
  4. somenath
    Replies:
    1
    Views:
    297
    Kalle Olavi Niemitalo
    Dec 23, 2007
  5. somenath

    pointer arithmetic question.

    somenath, May 6, 2012, in forum: C Programming
    Replies:
    10
    Views:
    612
    Tim Rentsch
    May 12, 2012
Loading...

Share This Page