【问题标题】:Convert a char* to uppercase in C without using a loop在不使用循环的情况下在 C 中将 char* 转换为大写
【发布时间】:2018-08-01 22:03:59
【问题描述】:

是否可以将 char* 转换为大写,而无需在循环中逐个字符地遍历?

假设:
1. 字符指针指向固定大小的字符串数组。
2.指向的数组只包含小写字符

【问题讨论】:

  • 如果知道字符串的最大长度,就可以展开循环。否则,不。
  • 使用递归而不是循环。
  • 不仅是 C,所有语言都必须使用循环或递归来实现您的请求。
  • 嗯...是的。可能是。您不必“逐个字符”地遍历。您可以一次说 4 或 8 个字符……取决于您的字长和内存对齐方式。转换为大写可以通过一次按位操作完成。
  • ...单位运算,前提是字符串只包含字母字符,并且使用的是ASCII字符集。

标签: c arrays string algorithm


【解决方案1】:

在 ASCII 编码中,将小写转换为大写相当于设置权重 32 的位(即 20H,space 字符)。

使用位运算符,

Char|= 0x20;

您可以通过在数组上映射更长的数据类型来一次处理多个字符。例如,要转换一个 11 个字符的数组,

int ToUpper= 0x20202020;

*(int*)  &Char[0]|=  ToUpper;
*(int*)  &Char[4]|=  ToUpper;
*(short*)&Char[8]|=  ToUpper;
          Char[10]|= ToUpper;

您可以使用 SIMD 内部函数(SSE、AVX)转至 64 位整数甚至更大(最多 512 位 = 一次 64 个字符)。

如果您的代码允许,最好将缓冲区长度扩展到下一个更大的数据类型,以便可以在单个操作中更新所有字节。但是不要忘记恢复终止的null。

【讨论】:

  • 这里有很多未定义的行为错误。 What is the strict aliasing rule?
  • @Lundin:请不要给我这个评论和downvote。目的显然是多字节处理黑客。
  • 看到人们如何对未定义的行为如此挑剔而忽略其他行为总是令人印象深刻。
  • @Lundin:我认为你不想理解我回答的目的。
  • 点赞。我正在阅读一些汇编/shellcode,他们这样做了。这是我在互联网上找到的唯一一篇回答我问题的帖子。
猜你喜欢
  • 2020-09-19
  • 2015-11-19
  • 2016-04-04
  • 2016-05-12
  • 2013-08-09
  • 2015-05-08
  • 2016-06-28
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多