第9周:字符串
C
9.1.1 字符串:字符串
字符数组
- char word[] = {'H','E','L','L','O','!'}; 
- 这不是C语言的字符串,因为不能用字符串的方式做计算
 
 
字符串
char word[] = {'H','E','L','L','O','!','\0'};
 
以0(整数0结尾的一串字符)
- 0(int, 4字节)或‘\0’(1字节)是一样的,但是和‘0’(ASCII码,48)不同
 
 
- 0标志字符串的结束,但它不是字符串的一部分 
 
- 字符串以数组的形式存在,以数组或指针的形式访问 
 
- string.h 里有很多处理字符串的函数
 
字符串变量
- char *str = "Hello";
 
- char word[] = "Hello";
 
- char line[10] = "Hello";
 
字符串常量
- “Hello”
 
- “Hello”会被编译器变成一个字符数组放在某处,这个数组的长度是6,结尾还有表示结束的0
 
- 两个相邻的字符串常量会被自动连接起来
 
字符串总结
- C语言的字符串是以字符数组的形态存在的 
- 不能用运算符对字符串做计算
 
- 通过数组的方式可以遍历字符串
 
 
- 唯一特殊的地方是字符串字面量可以用来初始化字符数组
 
- 以及C的标准库提供了一系列字符串函数
 
9.1.2 字符串:字符串变量
字符串常量
char * s = "Hello,world!";
- s是一个指针,初始化为指向一个字符串常量 
- 由于这个常量所在的地方,所以实际上s是const char* s,但是由于历史的原因,编译器不接受不带const的写法
 
- 但是试图对s所指的字符串做写入会导致严重的后果
 
 
- 如果需要修改字符串,应该用数组: 
char s[] = "Hello, world!"; 
指针还是数组?
- char *str = "Hello";
 
- char word[] = "Hello";
 
- 数组:这个字符串在这里 
 
指针:这个字符串不知道在哪里(只读不写)
 
如果要构造一个字符串-->数组
 
- 如果要处理一个字符串-->指针
 
char* 是字符串?
- 字符串可以表达为char*的形式
 
- char*不一定是字符串 
- 本意是指向字符的指针,可能指向的是字符的数组(就像int*一样)
 
- 只有它所指的字符数组有结尾的0,才能说它所指的是字符串
 
 
9.1.3 字符串:字符串的输入输出
字符串赋值?
- char *t = "title";
 
- char *s
 
- s = t
 
- 并没有产生新的字符串,只是让指针s指向了t所指的字符串,对s的任何操作就是对t做的
 
字符串输入输出
安全输入
- char string[8];
 
- scanf("%7s", string);
 
- 在%和s之间的数字表示最多允许读入的字符的数量,这个数字应该比数组的大小小一 
 
常见错误
- char *string
 
- scanf("%s", string);
 
- 以为char*是字符串类型,定义了一个字符串类型的变量string就可以直接用了 
- 由于没有对string初始化为0,所以不一定每次运行都出错
 
 
空字符串
- char buffer[100]=""; 
- 这是一个空的字符串,buffer[0] == '\0'
 
 
- char buffer[] = "" 
 
9.1.4 字符串:字符串数组,以及程序参数
字符串数组
- char **a 
- a是一个指针,指向另一个指针,那个指针指向一个字符(串)
 
 
- char a[][]
 
程序参数
- int main(int argc, char const *argv[])
 
- argv[0] 是命令本身 
 
9.2.1 字符串函数:单字符输入输出
putchar
- int putchar(int c);
 
- 向标准输出写一个字符
 
- 返回写了几个字符,EOF(-1)表示写失败
 
9.2.2 字符串函数:字符串函数strlen
string.h
- strlen
 
- strcmp
 
- strcpy
 
- strcat
 
- strstr
 
strlen
- size_t strlen(const char *s);
 
- 返回s的字符串长度(不包括结尾的0)
 
#include <stdio.h>#include <string.h>size_t mylen(const char *s){    int idx = 0;    while(s[idx] != '\0')   {        idx++;    }    return idx;}int main(int argc, char const *argv[]){    char line[] = "Hello";    printf("strlen=%lu\n", mylen(line));    printf("sizeof=%lu\n", sizeof(line));    return 0; } strlen=5sizeof=6    
9.2.3 字符串函数:字符串函数strcmp
strcmp
- int strcmp(const char *s1, const char *s2);
 
- 比较两个字符串,返回: 
- 0:s1 == s2
 
- 1:s1 > s2
 
- -1:s1 < s2
 
 
#include <stdio.h>#include <string.h>int mycmp(const char *s1, const char *s2){//  int idx = 0;//  while(s1[idx]==s2[idx] && s1[idx] !='\0'){////        if(s1[idx] != s2[idx]){////            break;////        } else if(s1[idx]=='\0'){////            break;////        }//      idx++;//  }    while(*s1==*s2 && *s1 != '\0'){        s1++;        s2++;    } //  return s1[idx]-s2[idx];    return *s1 - *s2;}int main(int argc, char const *argv[]){    char s1[] = "abc";    char s2[] = "abc ";    printf("%d\n", mycmp(s1,s2));    printf("%d\n", 'a'-'A');    return 0;}-3232
9.2.4 字符串函数:字符串函数strcpy
strcpy
- char *strcpy(char *restrict dst, const char *restrict src)
 
- 把src的字符串拷贝到dst 
 
- 返回dst 
 
复制一个字符串
- char *dst = (char *)malloc(strlen(src)+1);
 
- strcpy(dst,src);
 
#include <stdio.h>#include <string.h>char* mycpy(char* dst, const char* src){//  int idx = 0;//  while (src[idx]){//      dst[idx] = src[idx];//      idx++; //  }//  dst[idx] = '\0';    char* ret = dst;    while(*dst++ = *src++)        ;    *dst = '\0';    return ret;//  return dst;}int main(int argc, char const *argv[]){    char s1[] = "abc";    char s2[] = "abc";    mycpy(s1,s2);    return 0;}
9.2.5 字符串函数:字符串函数strcat
strcat
- char * strcat(char *restrict s1, const char *restrict s2);
 
- 把s2拷贝到s1的后面,接成一个长的字符串
 
- 返回s1
 
- s1必须具有足够的空间
 
安全问题
安全版本
- char * strncpy(char *restrict dst, const char *restrict src, size_t n);
 
- char * strncat(char *restrict s1, const char *restrict s2, size_t n);
 
- int strncmp(const char *s1, const char *s2, size_t n);
 
9.2.6 字符串函数:字符串搜索函数
在字符串中找字符
- char * strchr(const *s, int c);
 
- char * strrchr(const char *s, int c);
 
- 返回NULL表示没有找到
 
#include <stdio.h>#include <string.h>int main(int argc, char const *argv[]){    char s[] = "hello";    char *p = strchr(s, 'l');    char c = *p;    *p = '\0';//  p = strchr(p+1, 'l');    char *t = (char*)malloc(strlen(s)+1);    strcpy(t,s);    printf("%s\n", t);    free(t);    return 0;}he
字符串中找字符串
- char * strstr(const char *s1, const char *s2);
 
- char * strcasestr(const char *s1, const char *s2);