快速64位比较

时间:2010-03-02 15:33:53

标签: c++ string comparison

我正在开发一个GUI框架,我希望所有元素都由最多8个字符的ascii字符串标识(或者7可以)。

每次触发一个事件(有些只是点击,但有些是连续的),框架会使用id及其值回调客户端代码。

我可以使用实际的字符串和strcmp(),但我希望它非常快(对于移动设备),所以我想使用char常量(例如int id ='BTN1';)所以你会成为做一个int比较来测试id。但是,4个字符不够可读。

我尝试了一项实验,例如 - long int id = L'abcdefg';

...但看起来char常量只能容纳4个字符,并且唯一能产生long int char常量的东西就是你的4个字符宽度的两倍,而不是两倍的容量字符。我在这里错过了什么吗?

我想让编写客户端代码的人轻松一点。 gui存储在xml中,因此id是从字符串加载的,但是会在客户端代码中写入常量来比较这些常量。

所以,它的长期和短期是,我正在寻找一种跨平台的方式快速进行7-8字符比较,任何想法?

6 个答案:

答案 0 :(得分:4)

一种可能性是将您的ID定义为64位整数和8个字符的字符串的并集:

union ID {
  Int64 id;      // Assuming Int64 is an appropriate typedef somewhere
  char name[8];
};

现在你可以做以下事情:

ID id;
strncpy(id.name, "Button1", 8);
if (anotherId.id == id.id) ...

答案 1 :(得分:4)

您确定这不是过早优化吗?您是否已经分析了另一个纯粹来自字符串比较的GUI框架?为什么你这么确定字符串比较会太慢?当然你没有做 许多字符串比较。另外,考虑strcmp应该有一个接近最优的实现,可能是为你正在编译的CPU量身定制的组件。

无论如何,其他框架只使用命名整数,例如:

static const int MY_BUTTON_ID = 1;

您可以考虑相反,完全避免字符串问题。或者,您可以简单地编写一个辅助函数来将const char [9]转换为64位整数。这应该接受一个以空字符结尾的字符串“喜欢如此”,最多8个字符(假设您打算丢弃空字符)。然后你的程序传递64位整数,但程序员正在处理字符串。

编辑:这是一个将字符串转换为数字的快速函数:

__int64 makeid(const char* str)
{
    __int64 ret = 0;
    strncpy((char*)&ret, str, sizeof(__int64));
    return ret;
}

答案 2 :(得分:1)

易于获得预卷组件

获胜的

binary search tree - 您从大多数STL实现的set和map中获得了red-black树,因此您可能需要考虑这一点。

当你在很多地方移动容器节点时(在一般情况下),STL容器的

Intrusive versions表现得更好 - 但是它们有很多警告。

具体意见 - 第一选择

如果我是你,我会坚持使用64位整数类型并将其捆绑在一个侵入式容器中并使用boost提供的库。但是,如果您是这类新手,那么使用stl :: map它在概念上更容易掌握,并且它有更少的资源泄漏机会,因为有更多的文献和指南可用于这些类型的容器和最佳实践。

备选方案2

我想要解决的问题是:有一个映射到句柄的全局命名方案。您可以创建名称到句柄的映射,以便您可以使用名称来检索句柄:

// WidgetHandle is a polymorphic base class (i.e., it has a virtual method),
// and foo::Luv implement WidgetHandle's interface (public inheritance)
foo::WidgetHandle * LuvComponent = 
          Factory.CreateComponent<foo::Luv>( "meLuvYouLongTime");
....

.... // in different function
foo::WidgetHandle * LuvComponent = 
          Factory.RetrieveComponent<foo::Luv>("meLuvYouLongTime");

替代方案2是IPC的常用习惯用法,您可以在一个进程中创建IPC类型的管道,并且可以要求内核按名称检索管道的另一端。

答案 3 :(得分:1)

string interning的概念对此问题很有用,将字符串比较转换为指针比较。

答案 4 :(得分:0)

我看到代码中易于读取的标识符与传递的表示之间存在区别。

您可以使用枚举类型(或常量的大头文件)来表示标识符吗?根据您的意愿,枚举类型的名称可以是长的和有意义的,并且仍然适合(我猜)几个字节。

答案 5 :(得分:0)

在C ++ 0x中,您将能够使用user-defined string literals,因此您可以添加7chars..id"7chars.."id之类的内容:

template <char...> constexpr unsigned long long operator ""id();
constexpr unsigned long long operator ""id(const char *, size_t);

虽然我不确定你可以使用constexpr作为第二个。