GUN 工具 gperf 使用记录
GNU gperf 是一个完美的哈希函数生成器. 跟 flex bison 性质差不多, 就是通过一些规则文件生成代码, 不过一个是生成语法解析, 一个是生成 hash 函数.
https://www.gnu.org/software/gperf/
gperf 是一个命令行工具, 使用方式也很简单, 通过命令可以将一个 .gperf 后缀的文件生成一个 .c 文件
gperf test.gperf --output-file=test.c
--output-file 就是定义输出文件的路径, 除此之外还有其他参数可以使用, 可以通过 -h 参数查看帮助
除了将参数设置通过命令行传入, 还可以将设置参数直接写入 .gperf 文件, 下面就是一个例子
// Command-line: ./gperf test.gperf --output-file=test.c
%{
#include <stdio.h>
typedef enum
{
E_AAA,
E_BBB,
E_CCC,
E_DDD
} KEY;
%}
// 标准
%language=ANSI-C
// 忽略大小写
%ignore-case
// 使用结构体
%struct-type
// 查找表只读
%readonly-tables
// 使用 switch
%switch=1
// 比较函数
%compare-strncmp
// 包含必要头文件
%includes
// 全局
%global-table
// hash 函数名称 默认(hash)
%define hash-function-name hashFunc
// 查找函数名称 默认(in_word_set)
%define lookup-function-name lookUp
// 使用的表 默认(keyword)
%define word-array-name keyWord
// 结构体的 name 默认(name)
%define slot-name name
struct TAB
{
char *name;
KEY key;
};
%%
aaa, E_AAA
bbb, E_BBB
ccc, E_CCC
%%
int main(void)
{
char *test_str[] = {"aaa", "BBB", "eee"};
int i;
for(i=0; i<sizeof(test_str)/sizeof(test_str[0]); i++)
{
struct TAB *p = lookUp(test_str[i], strlen(test_str[i]));
if(p)
{
// 0:aaa
// 1:bbb
printf("%d:%s\n", p->key, p->name);
}
}
return 0;
}
大体结构这样
%{
// 放一些头文件, 定义
%}
// 定义规则, 结构体
%%
// 结构体初始化内容
%%
// 原样复制
这里需要注意一点的是, 定义结构体的时候不要 typedef, 否则可能报错 "multiple storage classes".