第六章:数组类型-2字符串

C 字符串

目标

在本文章中,您将学习C字符串以及如何有效地操作字符串。

介绍C字符串

字符串是字符序列。C语言没有内置的字符串类型。相反,它使用一个字符数组来定义字符串。因此,C语言中的字符串是一个字符数组。

为了标记字符串的结尾,C使用特殊字符'\0'。'\0'被称为空字符。当你显示字符串时,' \0 '不会显示。

null字符的ASCII码为0(零)。C不把空字符计算在字符串长度中。但是在定义字符串时,需要在数组中保留一个元素来存储空字符。

重要的是要注意null字符并不等同于null指针常量。

下面的例子定义了一个包含6个字符的字符串(包括空字符),将字符赋值给字符串数组元素,并在输出中显示该字符串:

#include <stdio.h>

int main()
{
    char message[6];

    // 赋值字符串元素
    message[0] = 'H';
    message[1] = 'e';
    message[2] = 'l';
    message[3] = 'l';
    message[4] = 'o';
    message[5] = '\0';

    // 显示字符串
    printf("%s", message);

   return 0;
}

输出:

Hello

它是怎么执行的。

  • 第一,定义字符串message,它是一个由6个字符组成的数组。
  • 第二,将字符分配给单个字符串元素。要结束一个字符串,将'\0'字符赋值给最后一个元素。
  • 第三,在输出中显示字符串。要显示字符串,可以使用%s格式说明符。
    C允许将字符串初始化为字符串字面量。在这种情况下,编译器将在字符串的末尾添加\0字符。例如:
char message[6] = "Hello";

在这个例子中,字符串“Hello”有5个字符。但是,您需要使用6作为数组的大小来存储空字符。

为了简单起见,可以将中括号置空:

char message[] = "Hello";

如果设置字符串的大小并在字符串中放入更多字符,就会得到字符串溢出错误。

将字符串字面量赋给字符串变量:

要定义字符串字面量,您需要将文本包含在双引号""中。例如:

"Hello"

因为C不允许你将一个数组赋值给另一个数组,所以你不能像这样将字符串字面量赋值给字符串变量:

message = "Hello";

相反,您需要使用标准库函数strcpy()将字符串字面量复制到变量。strcpy()复制整个字符串,包括空字符。要使用strcpy()函数,需要包含string.h标准库。

下面的示例演示了如何将message字符串初始化为“Hello”:

#include <stdio.h>
#include <string.h>

int main()
{
    char message[6];

    // 把“Hello”赋值给message
    strcpy(message, "Hello");

    printf("%s", message);

    return 0;
}

获得字符串长度:strlen()

c使用可变长度字符串。例如:

#include <stdio.h>
#include <string.h>

int main()
{
    char first_string[100] = "Hello";
    printf("%s", message);

    return 0;
}

这个例子定义了一个最多可以容纳100个字符的字符串。数组的大小为100。但是字符串的长度是5。

要获取字符串的长度,可以使用标准库函数strlen():

#include <stdio.h>
#include <string.h>

int main()
{
    // 把 "Hello" 赋值给字符串
    char first_string[100] = "Hello";

    // 获得字符串的长度
    int len = strlen(first_string);
    printf(" first_string 的长度是 %d", len);

    return 0;
}

将两个字符串连接成一个:strcat()

要将两个字符串连接成一个字符串,可以使用标准库函数strcat()。例如:

#include <stdio.h>
#include <string.h>

int main()
{
    char first_string[25] = "Hello",
        last_string[25] = "World",
        full_string[50];

    // 把first_string拷贝给full_string
    strcpy(full_string, first_string);
    // 连接“ ”和full_string
    strcat(full_string, " ");
    // 连接last_string和full_string
    strcat(full_string, last_string);

    // 显示full_string
    printf("%s", full_string);

    return 0;
}

输出:

Hello World

它是怎么执行的。
第一,声明三个变量用于存储三个字符串 first_stringlast_stringfull_string

    char first_string[25] = "Hello",
        last_string[25] = "World",
        full_string[50];

第二,拷贝字符串first_string到full_string:

    // 把first_string拷贝给full_string
    strcpy(full_string, first_string);

第三,连接字符串“ ”和full_string:

    // 连接“ ”和full_string
    strcat(full_string, " ");

第四,连接last_string和full_string:

    // 连接last_string和full_string
    strcat(full_string, last_string);

最后,显示full_string:

    // 显示full_string
    printf("%s", full_string);

从标准输入中读取一个字符串

标准函数fgets()允许从键盘(或标准输入)读取字符串。下面是fgets()函数的一般语法:

fgets(名字,sizeof(名字),stdin)

在这个语法:

  • 名称指定了一个字符串变量。
  • sizeof(名字)表示要读取的最大字符数(加1个null字符)。
  • stdin是标准输入,在本例中是键盘。
    如果按下Enter键,fgets()函数还会从键盘读取行尾字符(\n)。

下面的例子展示了如何从键盘读取字符串:

#include <stdio.h>
#include <string.h>

int main()
{
    char message[100];

    // 从输入中读取字符串
    fgets(message, sizeof(message), stdin);

    // 显示输入字符串
    printf("%s", message);
    printf("字符串的长度是 %d\n", strlen(message));

    // 显示字符
    for (int i = 0; i < strlen(message); i++)
    {
        if (message[i] == '\0')
            printf("message[%d] = NUL\n", i);
        else if (message[i] == '\n')
            printf("message[%d] = NEW_LINE\n", i);
        else
            printf("message[%d] = %c\n", i, message[i]);
    }

    return 0;
}

如果您输入消息hi并按enter,您将看到以下输出:

hi
hi
字符串的长度是 3
message[0] = h
message[1] = i
message[2] = NEW_LINE

可以看到,字符串的最后一个字符是新行字符(\n),而不是NUL字符(\0)。

要解决这个问题,你需要用\0结束字符串:

message[strlen(message) - 1] = '\0';

下面的程序通过使用NUL字符('\0')来修复从键盘读取的字符串:

#include <stdio.h>
#include <string.h>

int main()
{
    char message[100];

    // 从输入获得字符串
    fgets(message, sizeof(message), stdin);

    message[strlen(message) - 1] = '\0';
    // 显示输入字符串
    printf("%s\n", message);
    printf("字符串长度是 %d\n", strlen(message));

    return 0;
}

输出:

hi
hi
字符串长度是 2

比较两个字符串

要比较两个字符串,可以使用strcmp()函数。strcmp()比较每个字符串的第一个字符,如果它们相等,则继续每个字符串中的第二个字符,直到字符不同或达到NUL字符。

strcmp()如果第一个字符串在第二个字符串之前返回-1,如果两个字符串相等返回0,如果第一个字符串在第二个字符串之后返回1。

请看下面的例子:

#include <stdio.h>
#include <string.h>

int main()
{
    char sender[25] = "xiaoming",
         receiver[25] = "xiaowang";

    int result = strcmp(sender, receiver);

    printf("%d", result); // -1

    return 0;
}

输出:

-1

程序显示-1表示字符串“xiaoming”在“xiaowang”之前。

总结

  • 在C语言中,字符串是一个字符数组。字符串使用null字符('\0')来表示字符串的结束。
  • 使用strcpy()函数将一个字符串复制到另一个字符串。
  • strlen()函数的作用是:获取字符串的长度。
  • 使用strcat()函数将两个字符串连接成一个字符串。
  • 使用strcmp()函数比较两个字符串。
  • 在printf()函数中使用%s格式说明符向输出显示一个字符串。
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 205,132评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 87,802评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,566评论 0 338
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,858评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,867评论 5 368
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,695评论 1 282
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,064评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,705评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 42,915评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,677评论 2 323
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,796评论 1 333
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,432评论 4 322
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,041评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,992评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,223评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,185评论 2 352
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,535评论 2 343

推荐阅读更多精彩内容