Ragel字符串匹配

时间:2013-10-15 19:19:30

标签: pattern-matching ragel

我正在尝试为我正在进行的项目学习ragel。我是新来的。

我有一个包含15个字符串的列表。问题是检查给定的字符串是否与这15个字符串中的任何一个匹配。

在正常情况下,使用15个字符串构建哈希集就足以对字符串进行O(1)查找并判断它是否匹配。

在我的情况下,我将这样做十亿次。所以我正在尝试使用ragel为这15个字符串构建一个状态机,并检查给定的字符串是否匹配。

我觉得使用ragel方法更好,因为在这两种情况下我都必须逐个浏览角色。即为了计算哈希值,我们需要扫描一次所有字符,然后查看。使用状态机扫描所有字符一次给出结果并避免进行查找。

这是一种更好的方法吗?任何人都可以指出如何构建15个字符串的状态机来进行字符串匹配?

1 个答案:

答案 0 :(得分:0)

在某些体系结构上,通过正确的对齐,手工编码的*(int64_t*) "8 bytes" == *(int64_t*) a_c_string比较最有效,因为它使用单个CPU指令来比较7-8个字节。

Ragel没有最终的哈希表查找,但它有更多的branches,所以它是更快还是更慢 - 这取决于。我邀请你尝试一个完美的哈希(类似gperf),一个快速的通用哈希(dense_hash_map)和Ragel并分享结果。

以下是Ragel中的查找表的示例:

// ragel -G2 -o table_ragel.cc table.cc
int table (const char* cstring, int len) {
  char *p = (char*) cstring, *pe = p + len; int cs; %%{ machine table;
    main := ('foo' % {return 1;} | 'bar' % {return 2;});
    write data; write init; write exec; }%%
  return 0;
}
int main() {
  printf ("id: %i\n", table ("foo", 3));  // Prints 1.
  printf ("id: %i\n", table ("bar", 3));  // Prints 2.
  printf ("id: %i\n", table ("", 0));  // Prints 0.
  return 0;
}