Type Mismatching

Consider two methods. Both are called evaluate() and they are overloaded. The main() method calls evaluate("Hello world"). What version is called in the compiled code?

#include <iostream>
#include <string>

using namespace std;

void evaluate(bool value) {
    cout << "Evaluating a bool " << value << endl;
}

void evaluate(const std::string &value) {
    cout << "Evaluating a string " << value << endl;
}

int main() {
    evaluate("Hello world");
    return 0;
}

It may surprise you to know that the bool version is called and the compiler doesn't even complain about it either:

Evaluating a bool 1

This is an example of bad type inference. A string literal (a char ) should be turned into a std::string (a C++ string has a constructor that takes char ) but the compiler chose to treat it as a bool instead.

On other occasions the compiler might spot ambiguity and complain but the blurred lines between types in C++ combined with overloading lead to errors: Here is another example where the compiler is a little more useful by generating an error, but in doing so it demonstrates the limits of overloading

bool evaluate(bool value);
bool evaluate(double value);

These overloaded methods should be distinct but they're not distinct enough as far as the compiler is concerned.

In summary, blurred and confusing rules about types in C++ can cause unexpected errors that can propagate to runtime.

How Rust helps

In Rust the functions cannot be overloaded in this manner.

Rust is also more strict about type coercion - if you have a bool you cannot pass it to a function that takes an integer.

Nor can you pass an integer of one size to a function taking an integer of another size.

fn print_i32(value: i32) {
   println!("Your value is {}", value);
}
let value = 20i16; // 16-bit int
print_i32(value);

This will yield an error:

error[E0308]: mismatched types
  |
7 | print_i32(value);
  |           ^^^^^ expected i32, found i16

You must use an explicit numeric cast to turn the value into the type the function expects:

print_i32(value as i32);

results matching ""

    No results matching ""