c/c++字符串操作函数及用法详解

43 篇文章 1 订阅

1.strlen()函数

  1. 函数声明原型:
  2. 函数功能:

计算指定的字符串string的长度。

strlen函数实现:

size_t strlen(const char *string);
size_t my_strlen1(const char* string)
{
	assert(string);
	size_t count = 0;
	while (*string++)
	{
		count++;
	}
	return count;
}
size_t my_strlen2(const char* string)
{
	assert(string);
	if (*string == '\0')
		return 0;
	return 1 + my_strlen2(string + 1);
}
int main()
{
	char s[] = "abcdefg";
	printf("%d\n", my_strlen2(s));
	system("pause");
	return 0;
}

2.strcpy函数

原型:strcpy(str1,str2);

功能:将字符串str2复制到字符串str1中,并覆盖str1原始字符串,可以用来为字符串变量赋值

返回:str1

注意:1)字符串str2会覆盖str1中的全部字符,2)字符串str2的长度不能超过str1

char* my_strcpy(char* dest, const char* src)
{
	assert(dest);
	assert(src);
	char* ptr = dest;
	while (*src)
	{
		*dest++ = *src++;
	}
	*dest = *src;
	return ptr;
}
int main()
{
	char s1[] = "abefg";
	char s2[] = "cdefg";
	printf("%s\n", my_strcpy(s1, s2));
	system("pause");
	return 0;
}

3.strncpy函数

原型:strncpy(str1,str2,n);

功能:将字符串str2中的前n个字符复制到字符串str1的前n个字符中

返回:str1

注意:1)不会清除str1中全部字符串,只会改变前n个字符串,2)n不能大于字符串str1、str2的长度.

char str1[] = "We are csdn!";

char str2[] = "Hello!";

strncpy(str1, str2, 3);

printf("str1 = %s\n", str1); //str1 = Helare csdn!

4.strcat函数

原型:strcat(str1,str2);

功能:将字符串str2添加到字符串str1的尾部,也就是拼接两个字符串

原型2:strncat(str1,str2,n);

功能2:将字符串str2的前n个字符添加到字符串str1的尾部

返回:str1

注意:拼接之后的长度不能超过字符串数组str1的长度

#include<stdio.h>

#include<string.h>

int main()

{

char str1[20] = "We are csdn!";

char str2[] = "Hello!";

printf("%d\n",strlen(str1)); // 输出 12

printf("%d\n",sizeof(str1)); // 20

strcat(str1, str2);

printf("str1 = %s\n", str1); //str1 = We are csdn!Hello!

printf("%d\n",strlen(str1)); // 18

printf("%d\n",sizeof(str1)); // 20

}

5.strcmp函数

原型:strcmp(str1,str2);

功能:比较两个字符串,如果两个字符串相等,则返回0;

若str1大于str2(对于大于的理解,是指从两个字符串的第一个字符开始比较,若两个字符相同,则继续比较,若发现两个字符不相等,且str1中该字符的ASCII码大于str2中的,则表示str1大于str2),返回一个正数(这个正数不一定是1);

若str1小于str2,返回一个负数(不一定是-1);

若字符串str1的长度大于str2,且str2的字符与str1前面的字符相同,则也相当于 str1大于str2处理

原型2:strncmp(str1,str2,n);

功能2:比较两个字符串的前n个字符

原型3:stricmp(str1,str2); (在Windows中使用stricmp,在Linux中使用strcasecmp)

功能3:忽略两个字符串中的大小写比较字符串,也就是对大小写不敏感

int strcmp(const char *string1, const char *string2);//库函数原型
int my_strncmp(const char* s1, const char* s2, size_t count);

int my_strcmp(const char* s1, const char* s2)
{
	assert(s1);
	assert(s2);
	char* e1 = s1;
	char* e2 = s2;
	while ((*e1 == *e2) && (*e1 != '\0') && (*e2 != '\0'))
	{
		e1++;
		e2++;
	}
	if (*e1 > *e2)
		return 1;
	else if (*e1 < *e2)
		return -1;
	if (*e1 == *e2 == '\0')
		return 0;
}

int my_strncmp(const char* s1, const char* s2, size_t count)
{
	assert(s1);
	assert(s2);
	while ((count--) && (*s1 != '\0') && (*s2 != '\0'))
	{
		if (*s1 > *s2)
			return 1;
		if (*s1 < *s2)
			return -1;
		s1++; s2++;
	}
	if (*s1 != '\0')
		return 1;
	if (*s2 != '\0')
		return -1;
	return 0;
}
int main()
{
	char s1[] = "bcde";
	char s2[] = "cde";
	char sn1[] = "bcd";
	char sn2[] = "bcdd";
	printf("strncmp:%d\n", my_strncmp(sn1, sn2, 5));
	printf("strcmp:%d\n", my_strcmp(s1, s2));
	system("pause");
	return 0;
}
int main()
{
char buf2[5] ="Abbb", *buf1 = "cBBB" ;
int ptr;
    ptr = stricmp(buf2, buf1);
if(ptr>0)
        cout<<"buffer2 is greater than buffer1"<<endl;
if(ptr<0)
        cout<<"buffer2 is less than buffer1"<<endl;
if(ptr==0)
         cout<<"buffer2 equals buffer1"<<endl;
}

6.strchr函数

原型:strchr(str,c);

功能:在str字符串中查找首次出现字符c的位置(从字符串的首地址开始查找)

原型2:strrchr(str,c);

功能2:在字符串str中从后向前开始查找字符c首次出现的位置

原型3:strstr(str1,str2);

功能3:在字符串str1中查找字符串str2的位置,若找到,则返回str2第一个字符在str1中的位置的指针,若没找到,返回NULL

其原型为:char * strchr (const char *str, int c);

【参数】str 为要查找的字符串,c 为要查找的字符。

strchr() 将会找出 str 字符串中第一次出现的字符 c 的地址,然后将该地址返回。

注意:字符串 str 的结束标志 NUL 也会被纳入检索范围,所以 str 的组后一个字符也可以被定位。

【返回值】如果找到指定的字符则返回该字符所在地址,否则返回 NULL。

返回的地址是字符串在内存中随机分配的地址再加上你所搜索的字符在字符串位置。设字符在字符串中首次出现的位置为 i,那么返回的地址可以理解为 str + i。

提示:如果希望查找某字符在字符串中最后一次出现的位置,可以使用 strrchr() 函数。

【实例1】查找字符5首次出现的位置。

#include <stdio.h>

#include <stdlib.h>

#include <string.h>



int main(){

char *s = "0123456789012345678901234567890";

char *p;

p = strchr(s, '5');

printf("%ld\n", s);

printf("%ld\n", p);



system("pause");

return 0;

}

输出结果:

12016464

12016469

【实例2】

#include<stdio.h>

#include<string.h>

int main()

{

char str1[] = "Wearecsdn!";

char ch = 'e';

char str2[] = "are";

char* ret1;

char* ret2;

char* ret3;

ret1 = strchr(str1, ch); //ret1 = earecsdn!

ret2 = strrchr(str1, ch); //ret2 = ecsdn!

ret3 = strstr(str1, str2); //ret3 = arecsdn!

int r1 = ret1 - str1; //r1 = 1

int r2 = ret2 - str1; //r2 = 4

int r3 = ret3 - str1; //r3 = 2

printf("%s\n%s\n%s\n", ret1, ret2, ret3);

printf("%d\n%d\n%d\n", r1, r2, r3);

}

7.strpbrk函数

原型:strpbrk(str1,str2);

功能:依次检验字符串 str1 中的字符,当被检验字符在字符串 str2 中也包含时,则停止检验,并返回该字符位置

返回:第一个两个字符串中都包含的字符在str1中的位置的指针

#include < string .h >
#include < stdio.h >
 int  main()
 {
    char *str1="please try again,sky2098!";
    char *str2="Hello,I am sky2098,I like writing!";
    char *strtemp;
    strtemp=strpbrk(str1,str2);  //搜索进行匹配
    printf("Result is:  %s ",strtemp);
    return 0;
}

8.strspn函数

原型:strspn(str1,str2);

功能:检索字符串str1中第一个不在字符串str2中出现的字符下标

返回:返回 str1 中第一个不在字符串 str2 中出现的字符下标,一个int整数值

char str1[] = "We12are34csdn!";

char str2[] = "We32are1";

int len;

len = strspn(str1, str2); //len = 8

printf("%d\n", len);

9.strcspn函数

原型:strcspn(str1,str2);

功能:检索字符串str1开头连续有几个字符都不含字符串str2中的字符

返回:返回 str1 开头连续都不含字符串 str2 中字符的字符数,一个int整数值

char str1[] = "We12are34csdn!";

char str2[] = "32";

int len;

len = strcspn(str1, str2); //len = 3

printf("%d\n", len);

***************************************************************************************************

strpbrk、strcspn、strspn三个函数的区别:strpbrk是在字符串str1中查找第一个在字符串str2中也包含的字符的位置,返回该字符在str1中的位置指针,而strcspn返回的是该字符在str1中的偏移位置,strspn是在str1中查找第一个在str2不包含的字符的位置,返回该字符在str1中的偏移位置

***************************************************************************************************

10.strtod函数

原型:double strtod ( const char *nptr, char **endptr);

功能:strtod()会扫描参数nptr字符串,跳过前面的空格字符,直到遇上数字或正负符号才开始做转换,到出现非数字或字符串结束时('\0')才结束转换,并将结果返回。

若endptr不为NULL,则会将遇到不合条件而终止的nptr中的字符指针由endptr传回。参数nptr字符串可包含正负号、小数点或E(e)来表示指数部分。如123.456或123e-2。

#include <stdio.h>

#include <stdlib.h>

int main()

{

int index=0;

char *endpt=NULL;

char a[]="1234+9";

printf("a=%1f\n",strtod(a,&endpt));

index=endpt-a;

printf("index=%d",index);

return 0;

}

执行结果如下:

a=1234.000000,index=4

11.atoi、atof、atol函数

atoi(str); //字符串转换到int整型

atof(str); //字符串转换到double浮点数

atol(str); //字符串转换到long整形

#include<stdio.h>

//#include<string.h>

#include<stdlib.h>

int main()

{

char str[] = "123.34";

int chint = atoi(str); //chint = 123

double chdouble = atof(str); //chdouble = 123.340000

long int chlong = atol(str); //chlong = 123

printf("%d\n%f\n%ld\n", chint, chdouble, chlong);

}

string.h中还提供以下几种常用字符串操作函数:

1)void *memchr(const void *str, int c, size_t n) 在参数 str 所指向的字符串的前 n 个字节中搜索第一次出现字符 c(一个无符号字符)的位置,相似于strchr函数

2)int memcmp(const void *str1, const void *str2, size_t n)) 把存储区 str1 和存储区 str2 的前 n 个字节进行比较,相似于strncmp函数

3)void *memcpy(void *str1, const void *str2, size_t n) 从存储区 str2 复制 n 个字符到存储区 str1,相似于strncpy函数

4)void *memmove(void *str1, const void *str2, size_t n) 从 str2 复制 n 个字符到 str1,但是在重叠内存块这方面,memmove() 是比 memcpy() 更安全的方法。如果目标区域和源区域有重叠的话,memmove() 能够保证源串在被覆盖之前将重叠区域的字节拷贝到目标区域中,复制后源区域的内容会被更改。如果目标区域与源区域没有重叠,则和 memcpy() 函数功能相同

5)void *memset(void *str, int c, size_t n) 复制字符 c(一个无符号字符)到参数 str 所指向的字符串的前 n 个字符

#include<stdio.h>

#include<string.h>

int main()

{

char str1[] = "We are csdn!";

char* str2="ddd";

char* res=(char*) memcpy(str1,str2,2);

printf("%s\n",res); //dd are csdn!

memset(str1,'t',3);

printf("%s\n",str1); //tttare csdn!

}

6)字符串切割函数

函数原型:char *strtok(char *s, char *delim);

函数功能:把字符串s按照字符串delim进行分割,然后返回分割的结果。

函数使用说:

1.strtok函数的实质上的处理是,strtok在s中查找包含在delim中的字符并用NULL(’/0′)来替换,直到找遍整个字符串。这句话有两层含义:(1)每次调用strtok函数只能获得一个分割单位。(2)要获得所有的分割单元必须反复调用strtok函数。

2.strtok函数以后的调用时的需用NULL来替换s.

3.形参s(要分割的字符串)对应的变量应用char s[]=”….”形式,而不能用char *s=”….”形式。

例子如下:

#include <stdio.h>

#include <string.h>

int main(void)

{

char buf[]=”Golden Global View”;

char* token = strtok( buf, " ");

while( token != NULL )

{

printf( ”%s “, token );

token = strtok( NULL, ” “);

}

return 0;

}

其结果为:

Golden

Global

View

但是如果我们把char buf[]=”Golden Global View”;换成char *buf=”Golden Global View”; 则会出错,原因是如果分配的大小一样的前提下char *p和char b[]也是有区别的,

char *p=”abc”;

char b[]=”abc”;

当这两个语句编译后,编译器会将“abc”放在常量区中,而strtok(char *s, char *delim)函数是在s中查找包含在delim中的字符并用NULL(’/0′)来替换,直到找遍整个字符串。这句话就能体现指针和数组的区别:既然查找就要p++/b++。 要替换成(‘/0’),那么就要对*p/*b赋值

*p=’/0’;

*b=’/0’;

p指针是指向常量字符串的,对*p操作就是对字符串操作,这显然会编译不通过的。

b是字符数组的首地址,这个数组里面的元素是‘a’、’b’、’c’、’/0’,和字符串“abc”看上去是一样,不过并不是同一个。相当于,b数组里可以存放其他东西’1’、’2’、’3’、’/0’,只不过在编译到char b[]=”abc”;后给这个b数组里的元素值改变了,所以对*b的操作并不影响字符串。

如果我们把token = strtok( NULL, ” “);换成token = strtok( buf, ” “);则while循环会成为一个无限循环,而输出的结果就只为:Golden。我的解释原因如下: 在strtok函数体中有一个char 类型的指针(假设为 char *p),它的作用就是令p=s,用于保存s的起始地址。由于在随后的处理中指针p的值会一直保存(C语言中指针的特点),因此在以后的strtok调用中用NULL来代替s的原因就是防止p被重新赋值而指向s的起始地址,从而可以保证p可以指向s的其他位置,直到最后分割完整个字符串。 但是如果用s来代替NULL,那么每次调用strtok时,p就会指向s的初始地址,从而只能获得第一个分割出来的字串,如上面的例子中while会是一个无限循环,而输出的结果只能是“Golden”。

7).字符串中查找字串

strstr()函数用来检索子串在字符串中首次出现的位置,其原型为:

char *strstr( char *str, char * substr );

【参数说明】str为要检索的字符串,substr为要检索的子串。

【返回值】返回字符串str中第一次出现子串substr的地址;如果没有检索到子串,则返回NULL。

【函数示例】strstr()函数的使用。

#include<stdio.h>

#include<string.h>

int main(){

// 也可以改成 char str[] = "http://see.xidian.edu.cn/cpp/u/xitong/";

char *str = "http://see.xidian.edu.cn/cpp/u/xitong/";

char *substr = "see";

char *s = strstr(str, substr);

printf("%s\n", s);

return 0;

}

运行结果:

see.xidian.edu.cn/cpp/u/xitong/

8).获取字符串指定位置间的字符串

str.substr(startpos, length);

其中 startpos 是起始字符的序号,length 是[从 startpos 开始]取的字符串长度(包括

startpos )。

如果要取得 str 中序号 m 到 n 之间(不包括n)的子字符串需要用

str.substr(m, n-m);

#include<string>

#include<iostream>

using namespace std;

main()

{

string s("12345asdf");

string a=s.substr(0,4); //获得字符串s中 从第0位开始的长度为4的字符串

cout<<a<<endl;

}

输出结果为:

1234

9).c++中string提供的字符查找函数:

string中 find()的应用 ( rfind() 类似,只是从反向查找)

原型如下:

(1)size_t find (const string& str, size_t pos = 0) const; //查找对象-- string类对象

(2)size_t find (const char* s, size_t pos = 0) const; //查找对象-- 字符串

(3)size_t find (const char* s, size_t pos, size_t n) const; //查找对象-- 字符串的前n个字符

(4)size_t find (char c, size_t pos = 0) const; //查找对象-- 字符

结果:找到 -- 返回 第一个字符的索引

没找到--返回 string::npos

  • 12
    点赞
  • 73
    收藏
    觉得还不错? 一键收藏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值