Overloading the operator<

I am creating my own string class and was wondering if this was the right way to overload the less than operator to compare two char arrays

1
2
3
4
5
bool String::operator< (const String& rhs) const {

  return ch < rhs.ch;
}


I havent worked with < or > for chars in a long time so I am not sure how they work.

If I had
a= "abcd";
b= "mnop";

and call a<b should that be true or false?


Update
I should have said I am not allowed to use the string class I am making my own. So I can't use things like strcmp.
Last edited on
For pointers, < just compares the memory addresses, which is not what you want.

You could use the C string library function strcmp:
http://www.cplusplus.com/reference/cstring/strcmp/
In C (and this was inherited by C++) arrays decay to pointers.

This means that when you use an array you don't get its actual contents, but a pointer to the first element.

So when you do a<b it compares the memory address of the first element in a with the memory address of the first element in b. Which is not what you want, therefore you will use std::strcmp() or std::strncmp() instead, from the cstring library.

1
2
3
4
5
6
#include <cstring>

bool String::operator< (const String& rhs) const
{
    return std::strcmp(ch, rhs.ch) < 0;
}


http://www.cplusplus.com/reference/cstring/strcmp/
http://www.cplusplus.com/reference/cstring/strncmp/
Last edited on
As far as I can see from reading http://www.cplusplus.com/reference/string/string/operators/, overloading the < operator returns true if the FIRST LETTER of the string is less than (alphabetically) the first letter of the second string. So, in your case, a<b would return true.

Also, I don't think that you can use the < operator to compare 2 char arrays like that, because they could be different lengths (I might be wrong). They way I would think of doing that would be to iterate through the length of the smallest string, checking the operator as you go, and then returning based on that. Here is my quick example:

1
2
3
4
5
6
7
8
9
10
bool String::operator< (const String &rhs) const {
    if (ch == rhs.ch)    // You need to overload the == operator too
        return false;

    // Replace with your func/variable for length of string
    for (int i = 0; i < (len>rhs.len ? rhs.len : len); i++)
        if (ch[i] > rhs.ch[i]) return false;

    return len<rhs.len;
}


I haven't actually tested this, but I think it should work. Though, it is fairly inefficient, you could probably make it better.

EDIT:
Oh, just read posts above. I forgot about strcmp :)
Last edited on
He should use strcmp instead.
Or use std::string in the first place.
I should have said I am not allowed to use the string class I am making my own. So I can't use things like strcmp.

strcmp is a C function that compares two NULL-terminated character arrays. It has nothing to do with the std::string class.

It's exactly what you want here.
Last edited on
Update
I should have said I am not allowed to use the string class I am making my own. So I can't use things like strcmp.

Do not "update" your thread by editing editing the starting thread post, because it won't show up for us. Bump it with a reply.

The libraries names can be a bit confusing. In particular string.h which contains strcmp() is not the same as string which contains std::string.

Moreover, in C++ string.h has been renamed to cstring, with the former deprecated. Whether or not this was done just for the sake of incompatibility is a different topic.

Anyway, if you are explicitly forbidden from using std::strcmp(), which is stupid of your teachers, you can respond with equal stupidity by writing what is basically strcmp() yourself.

Just to be clear, I'm not calling you stupid, I'm just saying this restriction is stupid and therefore the "solution" will be stupid as well.

Disclaimer: the code below was not tested so it may contain bugs.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <cstddef>

bool String::operator < (const String &rhs) const
{
    std::size_t i=0; // for clarity, prefer using this type for sizes and lengths

    // '\0' is the NUL character
    // we could write a plain 0 instead, but we emphasize that it's a char

    while (ch[i] != '\0' && rhs.ch[i] != '\0')
        if (ch[i] == rhs.ch[i]) // they're equal, move up
            ++i;
        else
            break; // they're not equal, break the loop, then return

    return ch[i] < rhs.ch[i];
}


Edit: mistakes, and to dedicate this post to Vlad.
Last edited on
@CatFish,
return ch[i] < rhs.ch[i]; is it correct or it should be

return ch[i] == rhs.ch[i]; assume that both strings are equal

where are you vlad!
Catfish4 wrote:
Anyway, if you are explicitly forbidden from using std::strcmp(), which is stupid of your teachers, you can respond with equal stupidity by writing what is basically strcmp() yourself.
Or you can just open string.h file and copy-paste strcmp() function into your own program
where are you vlad!

Learning some manners, one hopes.

See:

http://www.cplusplus.com/forum/lounge/111264/
Last edited on
Who knows, he might have opened another account!
MiiNiPaa wrote:
Or you can just open string.h file and copy-paste strcmp() function into your own program
It's just a declaration for me, its definition is part of the compiled library file.
In that case library will be most likely linked anyway and copying declaration will work too.

Or you can google for library implementation:
http://www.jbox.dk/sanos/source/lib/string.c.html

Also: optimized strlen(): http://www.stdlib.net/~colmmacc/strlen.c.html
If you're going to use the standard library implementation of strcmp, then be explicit about it. Attempting to hide it by copying the prototype into your own header won't fool anyone.

In any case, the OP hasn't said that they're not allowed to use standard C library functions - only that they're not allowed to use a string class.
> In that case library will be most likely linked anyway and copying declaration will work too.

Copying a declaration from a standard header is not guaranteed to work.
Whether a name from the C standard library declared with external linkage has extern "C" or extern "C++" linkage is implementation-defined. It is recommended that an implementation use extern "C++" linkage for this purpose.
...
Footnote: The only reliable way to declare an object or function signature from the Standard C library is by including the header that declares it, notwithstanding the latitude granted in 7.1.7 of the C Standard. - IS
Topic archived. No new replies allowed.