Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

comparing strings with "<" or ">" operators (C)

Tags:

c

I try to understand if there is a defined behavior to the following operation in C:

char *str1 = "some string";
char *str2 = "another string";
if (*str1 > *str2)
    //do something...
else
    //do something else...

(As mentioned in the title, I mean to the "comparison" between the strings using ">" operator)

Obviously if I would try:

str1 > str2

(without the * operator)

it would calculate the results according to the pointer (i.e the string's address)(right..?). I searched answers for it but haven't found any, and I didn't succeed to understand it by playing with the code neither. thanks.

like image 938
noamgot Avatar asked Jan 26 '16 13:01

noamgot


3 Answers

With the indirection operator * you are actually comparing the values of the characters the pointers point to at the moment of the dereference.

So in your code, it's comparing 's' to 'a' as follows 's' > 'a' which is true.

The values have char type and hence it's well defined to use the <, > ==, >=, <=, != operators.

Be careful when declaring a pointer to a string literal, use the const qualifier to prevent accidentally modifying it because that would be undefined.

like image 124
Iharob Al Asimi Avatar answered Oct 20 '22 15:10

Iharob Al Asimi


In C, there is no "string type", just the convention that a char * pointing to a sequence of chars terminated by a null byte is called "string".

To compare string contents, use strcmp( const char *lhs, const char *rhs ).

*str1 > *str2 does not compare the strings, it compares their first characters.

str1 > str2 does not compare the strings either, and while it does "compare their addresses" on many platforms, strictly speaking it is undefined behaviour.

From the C standard, 6.5.8 Relational operators (which includes >), paragraph 5, emphasis mine:

When two pointers are compared, the result depends on the relative locations in the address space of the objects pointed to. If two pointers to object or incomplete types both point to the same object, or both point one past the last element of the same array object, they compare equal.

If the objects pointed to are members of the same aggregate object, pointers to structure members declared later compare greater than pointers to members declared earlier in the structure, and pointers to array elements with larger subscript values compare greater than pointers to elements of the same array with lower subscript values.

All pointers to members of the same union object compare equal. If the expression P points to an element of an array object and the expression Q points to the last element of the same array object, the pointer expression Q+1 compares greater than P.

In all other cases, the behavior is undefined.

like image 6
DevSolar Avatar answered Oct 20 '22 14:10

DevSolar


Without the * operator, you are actually comparing the addresses of str1 and str2, which causes undefined behavior, because they are not pointers to a same aggregate object or union or object.

With a * operator, however, you dereference their addresses, so what you compare becomes the values of the two string literals' first elements. In this code, there are no undefined behaviors.

like image 4
nalzok Avatar answered Oct 20 '22 14:10

nalzok