1

This question comes from this c++ how to replace a string in an array for another string

So if we have this code:

void foo( int i )
{
   i == 123;
}

we get compiler warning (from gcc v.5.0.1 -Wall):

warning: statement has no effect [-Wunused-value]

which is good, helpful and informative.

But if we do the same with std::string compiler is quiet:

void foo( std::string str )
{
    str == "foobar";
}

As I understand it is fine to ignore result of bool std::string::operator==() (as for any other function). But is there a way (or any plans to create one) to make compiler to generate warning for user defined types as well, so behavior of embedded types and user defined are closer?

PS I understand that it is not simple to make compiler to do that automatically. But what actually came to my mind is a way to tell compiler "generate warning when result of this function is ignored", aside of if there side effects or not. Is it possible? Are there bad side effects of this way?

Slava
  • 43,454
  • 1
  • 47
  • 90
  • 1
    The complete semantics for the builtin `operator==` are known to the compiler. `std::string::operator==` may have side effects (although it should not). – Richard Critten Sep 07 '17 at 15:51
  • 2
    The compiler would have to know that the intent of the type is to behave like `int` and other value types. One way, as a language extension, could be via an attribute `[[valuetype]]`. But it's a lot of machinery for little gain. – Cheers and hth. - Alf Sep 07 '17 at 15:52
  • 2
    Some compilers may have features, but nothing standard. e.g. GCC has `-Wno-unused-result` for `__attribute__ ((warn_unused_result))`, allthough you would also then need to be able to annoate the functions you want. – Fire Lancer Sep 07 '17 at 16:07
  • I found a discussion on GCC to always warn, but seems it was felt there were too many issues. I guess somthing would have to be proposed as a standard language feature so that the standardlibrary and other major libaries might add such annotations. https://gcc.gnu.org/ml/gcc-help/2016-10/msg00064.html – Fire Lancer Sep 07 '17 at 16:11

1 Answers1

3

The problem here is not only that operator== could have side effects, but also the conversion operator/constructor that transforms "foobar" to std::string will very likely have side effects, such as memory allocation.

Here is an illustration:

struct mystring {
    mystring(const char* str) {
        cout << "Constructed '" << str << "'" << endl;
    }
    bool operator==(const mystring& other) const {
        cout << "Compared" << endl;
        return false;
    }
};

When you do this

mystring a("hello");
a == "world";

the program prints

Constructed 'hello'
Constructed 'world'
Compared

As far as I know, there is no standard techniques to convince the compiler to report these situations. There are, however, non-standard techniques, e.g. __attribute__ ((warn_unused_result)) (thanks Fire Lancer), or Q&A on __attribute__((const)) and __attribute__((pure)) that let the compiler eliminate these calls.

Here is a modified demo in which __attribute__((warn_unused_result)) is used to generate a warning (I added a syntax error in order to make the warning visible on ideone).

Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523
  • Actually what I though something simpler, tell compiler to generate warning when result of particular function is ignored. – Slava Sep 07 '17 at 16:04