5

When I compile my C++ program using g++

warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
         for ( int i=0; i< myvec->size(); i++ ){
                                       ^

where myvec is an object of std::vector<float>.

For iterating over elements in std::vector, shall I need to deal with the warning? Thanks.

Tim
  • 1
  • 141
  • 372
  • 590
  • 4
    Possible duplicate of [What is wrong with my For loops? i get warnings: comparison between signed and unsigned integer expressions \[-Wsign-compare\]](http://stackoverflow.com/questions/7984955/what-is-wrong-with-my-for-loops-i-get-warnings-comparison-between-signed-and-u) – m.s. Aug 22 '16 at 14:59
  • Possible duplicate of [How can I fix warnings like: "comparison between signed and unsigned"?](http://stackoverflow.com/questions/859943/how-can-i-fix-warnings-like-comparison-between-signed-and-unsigned) – phuclv Mar 24 '17 at 13:40

3 Answers3

4

vector in c++ uses size_type to index the elements. You can write the for loop with this:

for(std::vector<float>::size_type i = 0; i < myvec->size(); i++) {
//code here
}

Another approach is to use iterators:

for(auto it = myvec->begin(); it != myvec->end(); ++it) {
//code here
}
KostasRim
  • 2,053
  • 1
  • 16
  • 32
3

std::vector<T>::size() returns std::vector<T>::size_type which is an unsigned integer type.

Consequently comparing with i in expression i < myvec->size(), which is of type int (i.e., signed integer), you rightfully get a warning because you are comparing an unsigned integer with a signed one.

The reason why you get this warning is that at their extrema (i.e., their maximum and minimum values), unsigned integers can become larger than their signed counterparts. The compiler issues a warning, in order to "ask"/"warn" you if you have taken into account any issues that might come up because of this.

If this is not a problem for you, you can amend the warning by simply casting.

for(int i(0); i < static_cast<int>(myvec->size()); ++i) {
  ...
}

Another way would be to change the type of i to match that of myvec->size():

for(std::vector<float>::size_type i(0); i < myvec->size(); ++i) {
  ...
}

Mind however that i becomes an unsigned integer type and if you're decreasing it in the loop you might get unexpected results (i.e., it won't get negative values).

Another way and if your compiler supports C++11 and if you want to loop over the elements of your vector without changing the vector itself, would be to use range based loop as:

for(auto &&e : *myvec) {
  ...
}

My personal favourite for looping over the elements of a vector is:

for(int i(0), sz(myvec->size()); i <sz; ++i) {
  ...
}
101010
  • 41,839
  • 11
  • 94
  • 168
0

101010 already explained the reason for this warning while comparing signed and unsigned integer expressions.

Nevertheless I would like to present one more approach to solve this warning. It is to use directly size_t instead of int for i.

for (size_t i = 0; i < myvec->size(); i++) {
  // ...
}

In stl_vector.h size_type is a type alias for size_t, so I think it should be safe to use that instead of having to write std::vector<float>::size_type like 101010 and KostasRim suggested, though that is way more expressive :-)

// [...]
typedef size_t size_type;
// [...]