Reputation: 63
I have written a driver in C++ for a peripheral device and in short, there is a number of errors that can occur during interaction. I have defined error codes for all the possible errors. I want to write a method that enables the user to query the meaning of error code.
Bear in mind that I have a total of 17 possible errors. The corresponding messages are of varying lengths.
I have solved it with a function that accepts the error code and returns a string with the error message. The function uses the error code to loop through a switch case routine each case returning a different error message as shown below.
std::string getErrorMessage(int errorCode)
{
std::string errorMessage = "no error" ;
switch(errorCode) {
case 0:
errorMessage = "no error" ;
break ;
case 10:
errorMessage = "there is a network error" ;
break ;
case 40:
errorMessage = "there is a network or protocol error" ;
break ;
default:
errorMessage = "unknown error" ;
}
return errorMessage ;
}
This function works, but it's not a "pretty" solution. Does anyone have any ideas or suggestions for a better solution?
Upvotes: 5
Views: 7040
Reputation: 6505
You can use a map to store the errors and initialize them in one place for everyone to see:
std::map<int,std::string> error_codes;
void init_codes()
{
error_codes[1231] = "error 1";
error_codes[121231] = "error 2";
error_codes[131231] = "error 3";
error_codes[135] = "error 4";
error_codes[10] = "error 5";
error_codes[0] = "error 6";
}
std::string get_error(const int e)
{
auto i = error_codes.find(e);
if( i != error_codes.end() )
{
//error was found
return (*i).second;
}
else
{
return "Unknown error";
}
}
Upvotes: 2
Reputation: 100658
If the error message are fixed, you are probably better off returning a const char*
.
It's a lot more efficient, involves no memory allocation and is convertible to a std::string
if necessary.
const char* getErrorMessage(int errorCode)
{
switch (errorCode) {
case 0: return "no error";
case 10: return "there is a network error";
case 40: return "there is a network or protocol error";
default: return "unknown error";
}
}
Upvotes: 1
Reputation: 42083
You could use std::map<int, std::string>
for mapping error messages to according codes:
std::string getErrorMessage(int errorCode)
{
static std::map<int, std::string> codes;
static bool initialized = false;
if (!initialized) {
codes[0] = "No error.";
codes[10] = "Network error.";
codes[40] = "Network or protocol error.";
initialized = true;
}
if (codes.count(errorCode) > 0)
return codes[errorCode];
return "Unknown error.";
}
Upvotes: 4
Reputation: 4322
If your error number is not large, using a table is more efficient
char *error[SIZE] =
{
[0] = "NO error",
[10] = "there is a network error",
[40] = "there is a network or protocol error",
....
}
You need some defensive check to make sure the error number is in range.
This is how glibc implments strerror() as I can recall.
Upvotes: 5
Reputation: 153919
If your error codes are sparse, the switch is probably the best solution. If you can make them dense, however, then you can just put the error messages in a table and use the error code to index into it.
Upvotes: 3