字符串和内存操作函数
来源:互联网 发布:淘宝3d试衣技术 编辑:程序博客网 时间:2024/04/26 11:42
1.1 字符串操作函数说明
对一串字符的处理在应用编程中无处不在,其操作函数主要有两类:一类以str开头的函数,主要针对字符串进行处理;一类为mem开头的函数,针对一片内存进行处理,此类函数可以处理字符串和结构体。
1.1.1 字符串操作函数总结说明
1. str与mem的含义
str开头的函数为字符串函数,字符串函数遇到'\0'结束符即终止操作,字符串最后一个字符即为'\0'字符。
mem开头的函数为一片内存操作函数,函数原型中包括处理长度,表示对一片内存空间的处理,这片内存中可以包含'\0'字符。
2. 会对目的串自动补’\0’字符的函数
常见有strcpy、sprintf、gets、strcat等不指定长度的字符串函数。
3. strcpy与memcpy的比较
对strcpy、memcpy两函数差别说明如下:
① strcpy用于字符串的复制,strcpy碰到源串'\0'字符即终止复制。
② memcpy为一片内存空间的复制,复制时可以包括'\0'字符,一片内存空间或结构体变量之间的复制常用此函数。
③ strcpy(dest,src)表示把源字符串src复制到目的串dest中,当dest空间小于src长度时会造成内存溢出,从而让程序coredump。
④ memcpy (dest , src, n)表示复制src所指的内存内容前n个字节到dest所指的内存地址上。如果是字符串复制可以用strncpy代替,不过strncpy遇到'\0'字符会终止复制,可能复制不到n个字节。
⑤ 两结构体变量之间的复制只能用memcpy函数。
4. strcpy与strncpy的比较
对strcpy、strncpy两函数差别说明如下:
① 用strcpy函数复制时目的串后会自动补0,用strncpy函数复制时目的串后不会自动补0。
② strncpy(dest, src, n)表示从src源串复制n个字节到dest目的串,但碰到'\0'字符时会提前终止复制。
③ 用strncpy函数时,有时需要给目的串设置结束符('\0'),给一串字符设置'\0'的方式有两种,分别为string[n]=0或string[n]= '\0'。因为字符可以当做整型单独赋值,0表示ASCII编号的0;也可以当做字符赋值,字符赋值时特殊字符需用\来转义。字符'0'的ASCII编号为30,而字符'\0'的ASCII编号为0。
1.2 字符串函数操作
字符串函数是编程中常用到的函数,字符串按照使用用途可分为字符串初始化、取字符串长度、复制字符串、连接字符串、比较字符串、搜索字符串、分割字符串七大类。
1. 字符串初始化
(1)函数原型
memset(将一段内存空间填入某值)
所需头文件
#include <string.h>
函数说明
memset()会将参数s所指的内存区域前n个字节以参数c填入,然后返回指向s的指针。在编写程序时,若需要将某一数组作初始化,memset()会相当方便
函数原型
void * memset (void *s ,int c, size_t n)
函数传入值
s:字符串地址
c:初始化字符
n:初始化字符串长度
函数返回值
返回指向s的指针
附加说明
参数c虽声明为int,但必须是unsigned char,所以范围在0到255之间
使用场合
① 初始化字符串
② 初始化结构体
③ 初始化malloc申请的内存空间
(2)memset函数说明
memset函数完成内存一片空间的初始化,对此函数使用方法说明如下:
① 字符串初始化:memset(string,0x00,sizeof(string)),string表示字符数组。
② 结构变量初始化:memset(&struct,0x00,sizeof(&struct)),struct表示结构变量。因为结构变量表示一片内存空间的抽象,需要用&得到结构变量地址。
③ 字符串和结构变量使用前最好用memset函数进行初始化。
(3)memset应用代码范例
memset.c代码如下:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
int main()
{
char s[30];
char *p ;
struct stu
{
int num;
char name[20];
char sex;
float score;
};
struct stu boy1;
p=(char *)malloc(1024);
memset (s, 0x00, sizeof(s));
memset(p, 0x00, 1024) ;
memset(&boy1, 0x00, sizeof(struct stu)) ;
return 0 ;
}
2. 取字符串长度
(1)函数原型
strlen(返回字符串长度)
所需头文件
#include <string.h>
函数说明
strlen()用来计算指定的字符串s的长度,不包括结束字符’\0’
函数原型
size_t strlen (const char *s)
函数传入值
s:字符串首地址
函数返回值
返回字符串s的字符数
(2)应用代码范例
strlen.c代码如下:
#include <stdio.h>
#include <string.h>
int main()
{
char *str = "12345678";
printf("str length = %d\n", strlen(str));
return 0 ;
}
编译 gcc strlen.c -o strlen。
执行 ./strlen,执行结果如下:
str length = 8
3. 复制字符串
(1)函数原型
strcpy(复制字符串)
所需头文件
#include <string.h>
函数说明
strcpy()会将参数src字符串复制至参数dest所指的地址
函数原型
char *strcpy(char *dest,const char *src)
函数传入值
dest:目的串地址
src:源串地址
函数返回值
返回参数dest的字符串起始地址
附加说明
如果参数dest所指的内存空间不够大,可能会造成缓冲溢出(buffer Overflow)的错误情况,在编写程序时请特别留意,或者用strncpy()来取代
strncpy(根据长度复制字符串)
所需头文件
#include <string.h>
函数说明
strncpy()会将参数src字符串复制前n个字符至参数dest所指的地址
函数原型
char * strncpy(char *dest,const char *src,size_t n)
函数传入值
dest:目的串地址
src:源串地址
n:复制的字符数
函数返回值
返回参数dest的字符串起始地址
memcpy(复制内存内容)
所需头文件
#include <string.h>
函数说明
memcpy()用来复制src所指的内存内容前n个字节到dest所指的内存地址上。与strcpy()不同的是,memcpy()会完整的复制n个字节,不会因为遇到字符串结束'\0'而结束
函数原型
void * memcpy (void * dest ,const void *src, size_t n)
函数传入值
dest:目的串地址
src:源串地址
n:复制字节数
函数返回值
返回指向dest的指针
附加说明
① 指针src和dest所指的内存区域不可重叠
② 结构体之间的复制需要用memcpy,而不能用strcpy
memmove(复制内存内容)
所需头文件
#include <string.h>
函数说明
memmove()与memcpy()一样都是用来复制src所指的内存内容前n个字节到dest所指的地址上。不同的是,当src和dest所指的内存区域重叠时,memmove()仍然可以正确的处理,不过执行效率上会比使用memcpy()略慢些
函数原型
void * memmove(void *dest,const void *src,size_t n)
函数传入值
dest:目的串地址
src:源串地址
n:复制字节数
函数返回值
返回指向dest的指针
(2)应用代码
strcpy.c源代码如下:
#include <stdio.h>
#include <string.h>
int main()
{
char a[30]="string(1)";
char b[]="string(2)";
printf("before strcpy() :%s\n",a);
printf("after strcpy() :%s\n",strcpy(a,b));
strncpy( &a[9], b, 9) ;
a[18]='\0' ;
printf("after strncpy():%s\n", a) ;
return 0 ;
}
编译 gcc strcpy.c -o strcpy。
执行 ./strcpy,执行结果如下:
before strcpy() :string(1)
after strcpy() :string(2)
after strncpy():string(2)string(2)
memcpy.c源代码如下:
#include <stdio.h>
#include <string.h>
int main()
{
char a[30];
char b[30]="string\0string";
int i;
memset( a, 0x00, sizeof(a) ) ;
strcpy(a,b);
printf("strcpy():", a);
for(i=0;i<30;i++)
printf("%c",a[i]);
printf("\n") ;
memcpy(a,b,30);
printf("memcpy():");
for(i=0;i<30;i++)
printf("%c",a[i]);
printf("\n") ;
return 0 ;
}
编译 gcc memcpy.c -o memcpy。
执行 ./memcpy,执行结果如下:
strcpy():string
memcpy():stringstring
4. 连接字符串
(1)函数原型
strcat(连接两字符串)
所需头文件
#include <string.h>
函数说明
strcat()会将参数src字符串复制到参数dest所指的字符串尾。第一个参数dest要有足够的空间来容纳要复制的字符串
函数原型
char *strcat (char *dest,const char *src)
函数传入值
dest:目的串地址
src:源串地址
函数返回值
返回参数dest的字符串起始地址
附加说明
如果参数dest所指的内存空间不够大,可能会造成缓冲溢出(buffer Overflow)的错误情况,在编写程序时请特别留意。
strncat(根据长度连接两字符串)
所需头文件
#include <string.h>
函数说明
strncat()会将参数src字符串复制n个字符到参数dest所指的字符串尾。第一个参数dest要有足够的空间来容纳要复制的字符串
函数原型
char * strncat(char *dest,const char *src,size_t n)
函数传入值
dest:目的串地址
src:源串地址
n:复制的字符数
函数返回值
返回参数dest的字符串起始地址
附加说明
strncat与strncpy不同,系统会对目的串结尾处自动补0
(2)应用代码范例
strcat.c源代码如下:
#include <stdio.h>
#include <string.h>
int main()
{
char a[30]="string(1)";
char b[]="string(2)";
printf("before strcat(): %s\n",a);
printf("after strcat(): %s\n",strcat(a,b));
printf("after strncat(): %s\n",strncat(a,b,6));
return 0 ;
}
编译 gcc strcat.c -o strcat。
执行 ./strcat,执行结果如下:
before strcat(): string(1)
after strcat(): string(1)string(2)
after strncat(): string(1)string(2)string
5. 比较字符串
(1)函数原型
strcmp(比较字符串)
所需头文件
#include <string.h>
函数说明
strcmp()用来比较参数s1和s2字符串。字符串大小的比较是以ASCII 码表上的顺序来决定,此顺序亦为字符的值。strcmp()首先将s1第一个字符值减去s2第一个字符值,若差值为0则再继续比较下个字符,若差值不为0则将差值返回。例如字符串"Ac"和"ba"比较则会返回字符'A'(65)和'b'(98)的差值(-33)
函数原型
int strcmp(const char *s1,const char *s2)
函数传入值
s1:串1
s2:串2
函数返回值
若参数s1和s2字符串相同则返回0。s1若大于s2则返回大于0的值。s1若小于s2则返回小于0 的值
strncmp(比较规定长度的字符串)
所需头文件
#include <string.h>
函数说明
用来将参数s1中前n个字符和参数s2字符串作比较
函数原型
int strcmp(const char *s1,const char *s2, size_t n)
函数传入值
s1:串1
s2:串2
n:比较字符串的长度
函数返回值
若参数s1和s2字符串相同则返回0。s1若大于s2则返回大于0的值。s1若小于s2则返回小于0 的值
memcmp(比较内存内容)
所需头文件
#include <string.h>
函数说明
memcmp()用来比较s1和s2所指的内存区间前n个字符。字符串大小的比较是以ASCII码表上的顺序来决定,次顺序亦为字符的值。memcmp()首先将s1第一个字符值减去s2第一个字符的值,若差为0则再继续比较下个字符,若差值不为0则将差值返回。例如,字符串"Ac"和"ba"比较则会返回字符'A'(65)和'b'(98)的差值(-33)
函数原型
int memcmp (const void *s1,const void *s2,size_t n)
函数传入值
s1:串1
s2:串2
n:比较字符串的长度
函数返回值
若参数s1和s2字符串相同则返回0。s1若大于s2则返回大于0的值。s1若小于s2则返回小于0 的值
附加说明
strcmp、strncmp碰到0字符即终止,而memcmp比较内容中可以包含0字符
忽略大小写比较字符串
所需头文件
#include <string.h>
函数说明
用来将参数s1中前n个字符和参数s2字符串作比较
函数原型
int strcasecmp(const char *s1, const char *s2)
int strncasecmp(const char *s1, const char *s2, size_t n)
函数传入值
s1:串1
s2:串2
n:比较字符串的长度
函数返回值
若参数s1和s2字符串相同则返回0。s1若大于s2则返回大于0的值。s1若小于s2则返回小于0 的值
(2)应用代码范例
strcmp.c源代码如下:
#include <stdio.h>
#include <string.h>
int main()
{
char *a="aBcDeF";
char *b="AbCdEf";
char *c="aacdef";
char *d="aBcDeF";
printf("strcmp(a,b) : %d\n",strcmp(a,b));
printf("strcmp(a,c) : %d\n",strcmp(a,c));
printf("strcmp(a,d) : %d\n",strcmp(a,d));
printf("strncmp(a,d,5 ) : %d\n",strncmp(a,d, 5));
printf("memcmp(a,d,3) : %d\n",memcmp(a,d,3));
printf("memcmp(a,b) : %d\n",strcasecmp(a,b));
printf("memcmp(a,b,4) : %d\n",strncasecmp(a,b,4));
return 0 ;
}
编译 gcc strcmp.c -o strcmp。
执行 ./strcmp,执行结果如下:
strcmp(a,b) : 1
strcmp(a,c) : -1
strcmp(a,d) : 0
strncmp(a,d,5 ) : 0
memcmp(a,d,3) : 0
memcmp(a,b) : 0
memcmp(a,b,4) : 0
6. 搜索字符串
(1)函数原型
strstr(在一字符串中查找指定的字符串)
所需头文件
#include <string.h>
函数说明
strstr()会从字符串haystack 中搜寻字符串needle,并将第一次出现的地址返回。
函数原型
char *strstr(const char *haystack, const char *needle)
函数传入值
haystack:源串
needle:搜索串
函数返回值
返回指定字符串第一次出现的地址,否则返回0
strchr(查找字符串中第一个出现的指定字符)
所需头文件
#include <string.h>
函数说明
strchr()用来找出参数s字符串中第一个出现的参数c字符的地址,然后将该字符出现的地址返回
函数原型
char * strchr (const char *s,int c)
函数传入值
s:源串
c:匹配字符
函数返回值
如果找到指定的字符则返回该字符所在地址,否则返回0
strrchr(查找字符串中最后出现的指定字符)
所需头文件
#include <string.h>
函数说明
strrchr()用来找出参数s字符串中最后一个出现的参数c字符的地址,然后将该字符出现的地址返回
函数原型
char * strrchr(const char *s, int c)
函数传入值
s:源串
c:匹配字符
函数返回值
如果找到指定的字符则返回该字符所在地址,否则返回0
(2)应用代码范例
strstr.c源代码如下:
#include <stdio.h>
#include <string.h>
int main()
{
char * s="0123456789012345678901234567890";
char *p;
p= strstr(s,"901");
printf("%s\n",p);
p=strchr(s,'5');
printf("%s\n",p);
p=strrchr(s, '8');
printf("%s\n",p);
return 0 ;
}
编译 gcc strstr.c -o strstr。
执行 ./strstr,执行结果如下:
9012345678901234567890
56789012345678901234567890
890
7. 分割字符串
(1)函数原型
strtok(分割字符串)
所需头文件
#include <string.h>
函数说明
strtok()用来将字符串分割成一个个片段。参数s指向欲分割的字符串,参数delim则为分割字符串,当strtok()在参数s的字符串中发现到参数delim字符时则会将该字符改为’\0’字符。在第一次调用时,strtok()必需给予参数s字符串,往后的调用则将参数s设置成NULL。每次调用成功则返回下一个分割后的字符串指针
函数原型
char * strtok(char *s,const char *delim)
函数传入值
s:源串
delim:分割符
函数返回值
返回下一个分割后的字符串指针,如果已无从分割则返回NULL
(2)应用代码范例
strtok.c源代码如下:
#include <stdio.h>
#include <string.h>
int main(void)
{
char str[] = "root:x::0:root:/root:/bin/bash:";
char *token;
token = strtok(str, ":");
printf("%s\n", token);
while ( (token = strtok(NULL, ":")) != NULL)
printf("%s\n", token);
return 0;
}
编译 gcc strtok.c -o strtok。
执行 ./strtok,执行结果如下:
root
x
0
root
/root
/bin/bash
1.3 字符类型测试函数
字符类型测试用来测试单个字符的类型。
(1)字符类型测试函数原型
头文件
#include <ctype.h>
函数原型
函数说明
int isalnum(int c)
测试字符是否为英文或数字
int isalpha(int c)
测试字符是否为英文字母
int isascii(int c)
测试字符是否为ASCII 码字符
int iscntrl(int c)
测试字符是否为ASCII 码的控制字符
int isdigit(int c)
测试字符是否为阿拉伯数字
int isgraph(int c)
测试字符是否为可打印字符(ASCII码33-126之间的字符)
int islower(int c)
测试字符是否为小写字母
int isprint(int c)
测试字符是否为包含空格在内可打印字符(ASCII码32-126之间的字符)
int isspace(int c)
测试字符是否为空格字符
int ispunct(int c)
测试字符是否为标点符号或特殊符号
int isupper(int c)
测试字符是否为大写英文字母
int isxdigit(int c)
测试字符是否为16进制数字
返回值
测试正确:返回TRUE或大于零的值
测试错误:NULL(0)
(2)应用代码范例
ischar.c源代码如下:
#include <stdio.h>
#include <ctype.h>
int main()
{
char str[]="123@#FDsP[e?";
int i;
for(i=0;str[i]!=0;i++)
if(islower(str[i])) printf("%c is a lower-case character\n",str[i]);
printf("1=%d\n", isxdigit('1')) ;
printf("2=%d\n", isxdigit('2')) ;
printf("v=%d\n", isxdigit('v')) ;
printf("U=%d\n", isupper('U')) ;
printf("u=%d\n", isupper('u')) ;
return 0 ;
}
编译 gcc ischar.c -o ischar。
执行 ./ischar,执行结果如下:
s is a lower-case character
e is a lower-case character
1=4096
2=4096
v=0
U=256
u=0
1.4 字符串转换函数
字符串转换函数完成数字到字符串、字符串到数字的转换功能,字符串转换函数是在应用编程中经常使用到的函数。
(1)字符串转换函数原型
atof(将字符串转换成浮点型数)
所需头文件
#include <stdlib.h>
函数说明
atof()会扫描参数nptr字符串,跳过前面的空格字符,直到遇上数字或正负符号才开始做转换,而再遇到非数字或字符串结束时('\0')才结束转换,并将结果返回。参数nptr字符串可包含正负号、小数点或E(e)来表示指数部分,如123.456或123e-2
函数原型
double atof(const char *nptr)
函数传入值
nptr:浮点型指针
函数返回值
返回转换后的浮点型数
atoi(将字符串转换成整型数)
所需头文件
#include <stdlib.h>
函数说明
atoi()会扫描参数nptr字符串,跳过前面的空格字符,直到遇上数字或正负符号才开始做转换,而再遇到非数字或字符串结束时('\0')才结束转换,并将结果返回
函数原型
int atoi(const char *nptr)
函数传入值
nptr:短整型指针
函数返回值
返回转换后的整型数
atol(将字符串转换成长整型数)
所需头文件
#include <stdlib.h>
函数说明
atol()会扫描参数nptr字符串,跳过前面的空格字符,直到遇上数字或正负符号才开始做转换,而再遇到非数字或字符串结束时('\0')才结束转换,并将结果返回
函数原型
long atol(const char *nptr)
函数传入值
nptr:长整型指针
函数返回值
返回转换后的长整型数
整型、长整型、浮点型转换为字符串
所需头文件
#include <stdio.h>
函数说明
通常可以用sprintf作变量类型转换
函数原型
int sprintf( char *str,const char * format, …)
转换例子
整型转换为字符串:sprintf(str, "%d", 30)
长整型转换为字符串:sprintf(str, "%ld", 300000)
浮点型转换为字符串:sprintf(str, "%.2f", 90.90)
(2)应用代码范例
ato.c源代码如下:
#include <stdio.h>
#include <stdlib.h>
int main()
{
char a[]="-100";
char aa[]="1000000000";
char *aaa="-100.23";
int c;
long cc ;
float ccc ;
char str[30];
c=atoi(a);
cc = atol(aa) ;
ccc = atof(aaa) ;
printf("c=%d\n",c);
printf("cc=%ld\n",cc);
printf("ccc=%.2f\n",ccc);
sprintf(str,"%d%ld%.2f",c, cc,ccc) ;
printf("str=%s\n", str) ;
return 0 ;
}
编译 gcc ato.c -o ato。
执行 ./ato,执行结果如下:
c=-100
cc=1000000000
ccc=-100.23
str=-1001000000000-100.23
摘录自《深入浅出Linux工具与编程》
- 字符串和内存操作函数
- 几个字符串和内存操作函数
- C语言内存操作函数和一般字符串操作函数
- 数学函数、字符处理函数、字符串和内存操作函数
- 内存与字符串操作函数
- C/C++ 内存块和字符串操作函数
- memset函数 及 内存操作函数 及 字符串操作函数
- 字符串以及内存操作相关函数
- 字符串以及内存操作相关函数
- 一些字符串及内存操作的函数
- Linux C 函数 内存及字符串操作
- 字符串以及内存操作相关函数
- 字符串以及内存操作相关函数
- 字符串基本操作以及内存函数
- 操作UNICODE、ANSI及多字节字符串函数的区别 和 内存分配注意事项
- 字符串操作和一级指针内存模型
- 【C语言】 字符串操作函数及内存拷贝函数归总
- C——常用字符串函数、内存操作函数总结
- 格式化I/O函数
- 线程安全的C++的Singleton实现
- 用主体+插件的方式构造软件
- C++/C 出现较多的面试题的答案与评分标准
- Thread.Join()和Thread.Sleep()
- 字符串和内存操作函数
- SQL2005级联删除,层叠,设置空,设置默认值
- 后台注册脚本文件
- 开篇
- linux下安装jdk
- C# DataGridView很全面的基本功能介绍
- cpu/arm920t/s3c2440/interrupts.c 解析
- C#获取网卡Mac地址
- ASP.NET中页面传值