项目用到了 Mysql,有很多相似代码,从一个表中取数据,赋值给一个结构体。将问题简化一下,如同这样:
结果集 A row_a[][128] = {"name", "20", "1000"}; 结构体 A struct A { char name[32]; int age; int money; }; 结果集 B row_b[][128] = {"jimmy", "100", "500", "1000", "lucy"}; 结构体 B struct B { char name[32]; int p1; int p2; int p3; char girlfriend[32]; };
写一个函数 func,能够用如下的方式,将不同的结果集分别赋值给对应的结构体。
A a; B b; func(&a, row_a); func(&b, row_b);
技巧一,在结构体中增加 static 成员变量,记录其成员类型信息。
struct A { static char keysinfo[]; char name[32]; int age; int money; }; char A::keysinfo[] = "sii"; s 表示字符串,定长 32 字节 i 表示 int
技巧二,写一个模板函数 func,大致的方法如下:
template <typename T, int M, int N> void func(T* st, const char (&str)[M][N]) { char * ptr = reinterpret_cast<char *>(st); for (int i = 0; i < M; ++i) { if (T::keysinfo[i] == 'i') { auto p = reinterpret_cast<int *>(ptr); *p = atoi(str[i]); ptr += 4; } else if (T::keysinfo[i] == 's') { strncpy(ptr, str[i], 32); ptr += 32; } } }
接下来,就实现了我们最初的想法,一个函数可以给不同的结构体赋值咯。
A a; char str[][128] = {"jimmy", "123", "456"}; func(&a, str); B b; char str[][128] = {"billy", "1000", "500", "100", "lucy"} func(&b, str);