【问题标题】:lower case string in cc中的小写字符串
【发布时间】:2025-12-07 06:00:01
【问题描述】:

我这里有几行:

#include <stdio.h>

char *tolower(char *data)
{
    char *p = data;
    while(*p)
    {
        printf("nilai p : %c\n",*p);
            if(*p >= 'A' && *p <= 'Z')
            {
                *p += ('a' - 'A');
            }
        p++;
    }
    return p;

}

int main()
{

    char *a = "HajAR BleH";
    char *b = tolower(a);

    printf("nilai b : %s\n",b);
    printf("nilai a - A : %d\n",'a' - 'A');
return 0;
}

下一步,编译,在 gdb 上运行,并跟踪分段

xxx@aaa:/tmp$ gcc -o aa aa.c --debug
xxx@aaa:/tmp$ gdb -q aa
Reading symbols from /tmp/aa...done.
(gdb) r
Starting program: /tmp/aa 
nilai p : H

Program received signal SIGSEGV, Segmentation fault.
0x0804841e in tolower (data=0x804855e "HajAR BleH") at aa.c:11
11                  *p += ('a' - 'A');
(gdb) 

问题

1. 我认为*p += ('a' - 'A'); 将等于'H' += ('a' - 'A') 并等于72 += 32 但是,意外的分段错误,怎么会呢?

2.为什么要加('a' - 'A')让char/byte变低?

暂时就这些了,先谢谢了

【问题讨论】:

  • 'a' - 'A' 没有意义,除非您熟悉 ASCII 表。 'a' 和 'A' 之间的数字差异是您必须添加到大写字母才能获得等效的小写字母。

标签: c string lowercase


【解决方案1】:

段错误的原因是您试图修改驻留在只读内存中的字符串文字,从而导致未定义的行为。

尝试改变

char *a = "HajAR BleH";

char a[] = "HajAR BleH";

【讨论】:

  • 其实是s/char \[\]a/char a\[\]/ ;) [] 是char类。
【解决方案2】:

1:基本上你的代码是正确的,但是你试图修改一个常量字符串(char *a应该重达const char *a)。您必须创建另一个可以修改的字符数组。

2:('a' - 'A') 计算小写字符和大写字符 (32) 之间的 ascii 值的“差异”。

【讨论】:

    【解决方案3】:

    除了只读内存的问题,你需要返回data而不是p。当您的循环完成时,p 指向空终止符。

    【讨论】:

      【解决方案4】:

      SEGV 最可能的原因是编译器已将 a 置于只读内存中,因为它允许对字符串文字进行处理。

      尝试将a的定义更改为:

      char a[] = "HajAR BleH";
      

      就风格而言,已经存在一个名为tolower 的标准函数,它做一些不同的事情(将一个字符 转换为小写)。考虑到这一点,我建议:

      1. 为您的函数指定不同的名称以避免混淆;
      2. 在您的实现中使用tolower 将一个字符转换为小写。

      【讨论】:

      • 即使我真的不在乎是否有任何函数 tolower() 存在,但感谢提醒我
      【解决方案5】:

      您正在尝试修改字符串文字。变化:

      char *a = "HajAR BleH";
      

      到:

      char a[] = "HajAR BleH";
      

      此外,已经有一个名为 tolower() 的标准库函数,您实际上应该在代码中使用它。调用你自己的函数。

      【讨论】: