C语言错误处理:如何通过错误码访问结构体字符串值
Hey there! Let's figure out how to map your error codes to their corresponding string messages in C. First, I'll fill in the logical gaps from the code snippet you shared (since you only showed ASCII definitions) and walk you through an idiomatic, safe way to solve this:
Step 1: Structure Your Enums and Error Info Properly
First, define your error code enum to be sequential starting at 0—this lets you use the enum values directly as array indices. Add a sentinel value at the end to track the total number of error codes, which helps with safety checks later.
#include <stdio.h> #include <string.h> #include <stdlib.h> /* ASCII Value Definitions */ #define ASCII_NULL 0x00 #define ASCII_HT 0x09 #define ASCII_NL 0x0A #define ASCII_CR 0x0D // Sequential error code enum (starts at 0, no gaps) typedef enum { ERR_SUCCESS = 0, // 0: Operation succeeded ERR_NULL_POINTER, // 1: Null pointer encountered ERR_INVALID_INPUT, // 2: Invalid input parameter ERR_MEMORY_ALLOC, // 3: Memory allocation failed ERR_MAX_COUNT // Sentinel: Total number of error codes } ErrorCode; // Struct to pair error codes with their human-readable messages typedef struct { ErrorCode code; const char* message; } ErrorInfo;
Step 2: Create a Mapped Array of Error Messages
Make an array of ErrorInfo where each entry's order exactly matches the order of your enum. This is the key to directly accessing messages via error codes.
// Error message lookup array (matches enum order) const ErrorInfo error_lookup[] = { {ERR_SUCCESS, "Operation completed successfully"}, {ERR_NULL_POINTER, "Null pointer detected in input"}, {ERR_INVALID_INPUT, "Received invalid input parameter"}, {ERR_MEMORY_ALLOC, "Failed to allocate required memory"} };
Step 3: Add a Safe Helper Function for Access
Wrap the lookup logic in a function to add boundary checks—this prevents invalid memory access if someone passes an out-of-range error code.
// Retrieve error message by error code const char* get_error_message(ErrorCode code) { // Validate the error code first if (code < 0 || code >= ERR_MAX_COUNT) { return "Unknown error code"; } // Direct index access (fast and simple) return error_lookup[code].message; }
Step 4: Test It in Action
Here's how you'd use this setup in your code:
int main() { // Example 1: Memory allocation error ErrorCode my_error = ERR_MEMORY_ALLOC; printf("Error %d: %s\n", my_error, get_error_message(my_error)); // Example 2: Invalid input error my_error = ERR_INVALID_INPUT; printf("Error %d: %s\n", my_error, get_error_message(my_error)); // Example 3: Invalid code (safety check triggers) my_error = 99; // Out of valid error code range printf("Error %d: %s\n", my_error, get_error_message(my_error)); return 0; }
What If Your Enums Aren't Sequential?
If your error codes have gaps (e.g., reserved for external APIs), use a loop to search for the matching code instead:
const char* get_error_message(ErrorCode code) { for (int i = 0; i < ERR_MAX_COUNT; i++) { if (error_lookup[i].code == code) { return error_lookup[i].message; } } return "Unknown error code"; }
This is slightly slower, but works perfectly with non-sequential error codes.
内容的提问来源于stack exchange,提问作者Anthony Gladiator

