An explicit conversion is what you're calling a cast. An implicit conversion is a conversion between types that the compiler allows or performs, even if you don't do a cast. For example;
The initialisation of j involves an implicit conversion of an int to a long. The compiler knows how to do that, so it happens implicitly (as far as the programmer is concerned).
Conversion between basic types are built in: for example, the compiler knows how to add an int to a double.
Class types support conversions in two ways: by the constructors they supply, and by operator functions.
class X
{
public:
X(const char *);
};
allows a const char pointer to be converted to an X. Given a function;
the call
will create a temporary X by passing "Hello" to its constructor, and then pass that temporary to func(). That process of creating the temporary X from "Hello" is a conversion.
The other way is that;
class Y
{
public:
operator const char *() const; // conversion to const char *
};
declares an operator that allows a Y to be converted to a const char *. So, given;
void another_func(const char *);
it is possible to do this;
Y y; / assume we have a default constructor
another_func(y);
as the compiler will implicitly invoke the operator const char *() for the object y, and pass the result to another_func().
Because of all that, you control the conversions supported by a class by controlling what constructors it supports and what conversion operators it supports. Constructors can be used to do conversions. However, prefixing the constructor keyword to the constructor declaration prevents it from being used to do implicit conversions (and some other things).
std::string::c_str() returns a const char *. However, std::string does not supply an operator const char *().
Converting a float to an int rounds towards zero. That involves dropping the decimal places for small values. However, that doesn't work for larger values. For example, assume your compiler supports a 32 bit float and a 32 bit int (fairly commonly true). The float can represent the value 3.4E+30. What would you expect to happen if you convert that value to an int (which can only hold values in the range -2,147,483,648 to 2,147,483,647)?