一、字符串函数
1、gets()
头文件:#include <stdio.h>
函数原型:char *gets(char *string);
函数说明:从标准输入流(stdin)中读取整行,直至遇到换行符结束,然后丢弃换行符,储存其余字符,并在末尾加上空字符,表示一个字符串;
函数返回值:若成功则返回指向string的指针,否则返回NULL;
备注:与puts()函数配套使用;只知道string的开始出,不知道数组中有多少个元素,超出边界,容易造成缓冲区溢出。
2、fgets()
头文件:include<stdio.h>
函数原型:char *fgets(char *string, int size, FILE *stream);
函数说明:从输入流( FILE *stream)中读取整行;如果size设为n,将从输入流中读取n-1个字符,或者遇到换行符结束(包含换行符),存储在string中,并在末尾添加空字符,表示一个字符串;
函数返回值:读取成功,返回读取到的字符串,即string;失败或读到文件结尾返回NULL。因此,我们不能直接通过fgets()的返回值来判断函数是否是出错而终止的,应该借助feof()函数或者ferror()函数来判断;
备注:与fputs()配套使用。
3、puts()
头文件:#include<stdio.h>
函数原型:int puts(char *string);
函数说明:puts()函数用于将一字符串输出到标准输出流(stdout)中,直到遇见结束标志 ' ',' '不会被输出到stdout,并在最后增加换行符 ' ';
返回值:输出成功返回非0值,否则返回0;
4、fputs()
头文件:#include <stdio.h>
函数原型:int fputs(char *string, FILE *stream);
函数说明:fputs()从string的开头向文件写入字符串,直到遇见结束字符 ' ',' ' 不会被写入到文件中,不添加换行符;
备注:fputs()可以指定输出的文件流,不会输出多余的字符;puts()只能向 stdout 输出字符串,而且会在最后自动增加换行符。
5、strcat()
头文件:#include <string.h>
函数原型:char *strcat(char *dest, const char *src);
函数说明:strcat() 会将参数 src 字符串复制到参数 dest 所指的字符串尾部;dest 最后的结束字符 NULL 会被覆盖掉,并在连接后的字符串的尾部再增加一个 NULL,空字符是结束标志;
返回值:返回dest 字符串起始地址;
备注:dest 与 src 所指的内存空间不能重叠,且 dest 要有足够的空间来容纳要复制的字符串。
6、strncat()
头文件:#inclue <string.h>
函数原型:char * strncat(char *dest, const char *src, size_t n);
函数说明:strncat()将会从字符串src的开头拷贝n 个字符到dest字符串尾部,dest要有足够的空间来容纳要拷贝的字符串。如果n大于字符串src的长度,那么仅将src全部追加到dest的尾部;strncat()会将dest字符串最后的' '覆盖掉,字符追加完成后,再追加' ';
返回值:返回字符串dest。
7、strcmp()
头文件:#include <string.h>
函数原型:int strcmp(const char *s1, const char *s2);
函数说明:strcmp() 用来比较字符串(区分大小写);字符串大小的比较是以ASCII 码表上的顺序来决定,此顺序亦为字符的值。strcmp()首先将s1 第一个字符值减去s2 第一个字符值,若差值为0 则再继续比较下个字符,若差值不为0 则将差值返回。例如字符串"Ac"和"ba"比较则会返回字符"A"(65)和'b'(98)的差值(-33);
返回值:若参数s1 和s2 字符串相同则返回0。s1 若大于s2 则返回大于0 的值。s1 若小于s2 则返回小于0 的值;
备注:strcmp() 以二进制的方式进行比较,不会考虑多字节或宽字节字符;如果考虑到本地化的需求,请使用 strcoll()函数。
8、strncmp()
头文件:#include <string.h>
函数原型:int strncmp ( const char * str1, const char * str2, size_t n );
函数说明:strncmp() 用来比较两个字符串的前n个字符,区分大小写;字符串大小的比较是以ASCII 码表上的顺序来决定,此顺序亦为字符的值。strncmp()首先将s1 第一个字符值减去s2 第一个字符值,若差值为0 则再继续比较下个字符,直到字符结束标志' ',若差值不为0,则将差值返回。例如字符串"Ac"和"ba"比较则会返回字符"A"(65)和'b'(98)的差值(-33)。
返回值:若str1与str2的前n个字符相同,则返回0;若s1大于s2,则返回大于0的值;若s1 若小于s2,则返回小于0的值;
备注:要比较的字符包括字符串结束标志' ',而且一旦遇到' '就结束比较,无论n是多少,不再继续比较后边的字符。
注意:如果两个字符不同,GCC返回该字符对应的ASCII码的差值,VC返回-1或1。但是让人为难的是,strnicmp()、strcmp()、stricmp()在GCC和VC下都返回-1或1,而不是ASCII的差值。
9、strcpy()
头文件:#include <string.h>
函数原型: char *strcpy(char *dest, const char *src);
函数说明:strcpy() 函数用来复制字符串;strcpy() 把src所指的由' '结束的字符串(包含空字符)复制到dest 所指的数组中(且可以不必指向数组的开始),返回指向 dest 字符串的起始地址,即只拷贝空字符(包含空字符)之前的所有的字符,忽略其后的所有字符。
返回值:成功执行后返回目标数组指针 dest;
备注:src 和 dest 所指的内存区域不能重叠,且 dest 必须有足够的空间放置 src 所包含的字符串(包含结束符NULL);如果参数 dest 所指的内存空间不够大,可能会造成缓冲溢出(buffer Overflow)的错误情况,在编写程序时请特别留意,或者用strncpy()来取代。
10、strncpy()
头文件:#include <string.h>
函数原型:char * strncpy(char *dest, const char *src, size_t n);
函数说明:strncpy()用来复制字符串的前n个字符;如果src的字符数少于n个,目标字符串就以拷贝的空字符结尾;如果src的字符数有n个或超过n个,就不拷贝空字符;
返回值:返回字符串dest;
备注:src 和 dest 所指的内存区域不能重叠,且 dest 必须有足够的空间放置n个字符;还要注意不拷贝空字符的情况。
11、sprintf()
头文件:#include <stdio.h>
函数原型:int sprintf(char *str, char * format [, argument, ...]);
函数说明:sprintf()函数用于将格式化的数据写入字符串;str为要写入的字符串;format为格式化字符串,与printf()函数相同;argument为变量;sprintf()会根据参数format 字符串来转换并格式化数据,然后将结果复制到参数str 所指的字符串数组,直到出现空字符结束(' ')为止;
备注:sprintf的作用是将一个格式化的字符串输出到一个目的字符串中,而printf是将一个格式化的字符串输出到屏幕。sprintf的第一个参数应该是目的字符串,如果不指定这个参数,执行过程中出现 "该程序产生非法操作,即将被关闭...."的提示;C语言对数组进行操作时并不检测数组的长度,如果str的长度不够,sprintf()很容易造成缓冲区溢出,带来意想不到的后果,黑客经常利用这个弱点攻击看上去安全的系统。
12、strchr()
头文件:#include <string.h>
函数原型:char * strchr (const char *str, int c);
函数说明:查找某字符在字符串中首次出现的位置;strchr() 将会找出 str 字符串中第一次出现字符 c 的地址,然后将该地址返回;
返回值:如果找到指定的字符则返回该字符所在地址,否则返回 NULL。
备注:字符串 str 的结束标志 ' ', 也会被纳入检索范围,所以 str 的组后一个字符也可以被定位。
13、strrchr()
头文件:#include <string.h>
函数原型:char * strrchr(const char *str, int c);
函数说明:查找某字符在字符串中最后一次出现的位置;将会找出 str 字符串中最后一次出现字符 c 的地址,然后将该地址返回;
返回值:如果找到就返回该字符最后一次出现的位置,否则返回 NULL。
备注:字符串 str 的结束标志' ', 也会被纳入检索范围,所以 str 的组后一个字符也可以被定位。
14、strpbrk()
头文件:#include <string.h>
函数原型:char *strpbrk( char *s1, char *s2);
函数说明:检索两个字符串中首个相同字符的位置;strpbrk()从s1的第一个字符向后检索,直到' ',如果当前字符存在于s2中,那么返回当前字符的地址,并停止检索。
返回值:如果s1、s2含有相同的字符,那么返回指向s1中第一个相同字符的指针,否则返回NULL。
备注:strpbrk()不会对结束符' '进行检索。
1 #include<stdio.h> 2 #include<string.h> 3 int main(void){ 4 char* s1 = "http://see.xidian.edu.cn/cpp/u/xitong/"; 5 char* s2 = "see"; 6 char* p = strpbrk(s1,s2); 7 if(p){ 8 printf("The result is: %s ",p); 9 }else{ 10 printf("Sorry! "); 11 } 12 return 0; 13 } 14 15 结果: 16 The result is: see.xidian.edu.cn/cpp/u/xitong/
15、strstr()
头文件:#include <string.h>
函数原型: char *strstr( char *str, char * substr );
函数说明:用来检索子串在字符串中首次出现的位置;
返回值:返回字符串str中第一次出现子串substr的地址;如果没有检索到子串,则返回NULL。
1 #include<stdio.h> 2 #include<string.h> 3 int main(){ 4 // 也可以改成 char str[] = "http://see.xidian.edu.cn/cpp/u/xitong/"; 5 char *str = "http://see.xidian.edu.cn/cpp/u/xitong/"; 6 char *substr = "see"; 7 char *s = strstr(str, substr); 8 printf("%s ", s); 9 return 0; 10 } 11 12 结果: 13 see.xidian.edu.cn/cpp/u/xitong/
16、strlen()
头文件:#include <string.h>
函数原型:unsigned int strlen (char *s);
函数说明:计算指定的字符串s 的长度,不包括结束字符' ';
注意:
一下字符数组,例如
char str[100] = "http://see.xidian.edu.cn/cpp/u/biaozhunku/";
定义了一个大小为100的字符数组,但是仅有开始的11个字符被初始化了,剩下的都是0,所以 sizeof(str) 等于100,strlen(str) 等于11。
如果字符的个数等于字符数组的大小,那么strlen()的返回值就无法确定了,例如
char str[6] = "abcxyz";
strlen(str)的返回值将是不确定的。因为str的结尾不是0,strlen()会继续向后检索,直到遇到' ',而这些区域的内容是不确定的。
strlen() 函数计算的是字符串的实际长度,遇到第一个' '结束。如果你只定义没有给它赋初值,这个结果是不定的,它会从首地址一直找下去,直到遇到' '停止。而sizeof返回的是变量声明后所占的内存数,不是实际长度,此外sizeof不是函数,仅仅是一个操作符,strlen()是函数。
17、memchr()
头文件:#include <string.h>
函数原型:void * memchr(const void *s, char c, size_t n);
函数说明:memchr()从头开始搜寻s 所指的内存内容前n 个字节,直到发现第一个值为c 的字节,则返回指向该字节的指针。
返回值:如果找到指定的字节则返回该字节的指针,否则返回NULL。
18、memcmp()
头文件:#include <string.h>
定义函数:int memcmp (const void *s1, const void *s2, size_t n);
函数说明:memcmp()用来比较s1 和s2 所指的内存区间前n 个字符,适用于任何数据类型。
字符串大小的比较是以ASCII 码表上的顺序来决定,次顺序亦为字符的值。memcmp()首先将s1 第一个字符值减去s2 第一个字符的值,若差为0 则再继续比较下个字符,若差值不为0 则将差值返回。例如,字符串"Ac"和"ba"比较则会返回字符'A'(65)和'b'(98)的差值(-33)。
返回值:若参数s1 和s2 所指的内存内容都完全相同则返回0 值。s1 若大于s2 则返回大于0 的值。s1 若小于s2 则返回小于0 的值。
1 #include <string.h> 2 main(){ 3 char *a = "aBcDeF"; 4 char *b = "AbCdEf"; 5 char *c = "aacdef"; 6 char *d = "aBcDeF"; 7 printf("memcmp(a, b):%d ", memcmp((void*)a, (void*)b, 6)); 8 printf("memcmp(a, c):%d ", memcmp((void*)a, (void*)c, 6)); 9 printf("memcmp(a, d):%d ", memcmp((void*)a, (void*)d, 6)); 10 }
19、memcpy()
头文件:#include <string.h>
memcpy() 用来复制内存,其原型为:
void * memcpy ( void * dest, const void * src, size_t num );
memcpy() 会复制 src 所指的内存内容的前 num 个字节到 dest 所指的内存地址上。
memcpy() 并不关心被复制的数据类型,只是逐字节地进行复制,这给函数的使用带来了很大的灵活性,可以面向任何数据类型进行复制。
需要注意的是:
- dest 指针要分配足够的空间,也即大于等于 num 字节的空间。如果没有分配空间,会出现断错误。
- dest 和 src 所指的内存空间不能重叠(如果发生了重叠,使用 memmove() 会更加安全)。
与 strcpy() 不同的是,memcpy() 会完整的复制 num 个字节,不会因为遇到“