字符串相关的题目

字符串

字符串函数

头文件string.h
1.求字符串长度

// An highlighted block
char p[10]="hello";
printf("字符串长度为%d",strlen(p));//输出为5;(不为10,也不是包含\0的6)

2.字符串连接

// An highlighted block
char p1[10]="hello",p2[]="world";
strcat(p1,p2);//将p2连接到p1上
puts(p1);// helloworld
///puts和printf的对比

3.字符串复制

// An highlighted block
char p1[10]="hello",p2[10];
strcpy(p2,p1);//将p1内容赋值到p2


以下的做法是错误的
char p[10]="hello",p2[10];
p2=p1;

4.字符串的比较(*)

// An highlighted block
char p1[10]="hello",p2[10]="hellow";
strcmp(p1,p2);
/*
p1和p2逐个比较直到不等或者一个结束.
三种情况,p1>p2:返回正数,p1=p2:返回0,p1<p2:返回负数
*/

5.从字符串提取特殊子串

// An highlighted block
char p1[10]="123AbcEFG123";
char buff[10];

//取数字和和大写字母
sscanf(p1,"%[1-9A-Z]",buff);
puts(buff);//123A   遇到不符合的就会停止,所以不会有后面EFG123
/*
sscanf(p1,"%d",a); //可以直接转换数据类型
printf("%d",a);
*/
//直到符号和跳过符号
sscanf(p1,"%[^A-Z]",buff);//遇到大写就停止
puts(buff);//123
sscanf(p1,"%*[A-Z]",buff);//跳过大写符号
puts(buff);//123bc123

sscanf(p1,"%*[^A-Z]",buff);//跳过非大写符号,即只要大写
puts(buff);//AEFG

可以取多个值,在txt文件的提取参数中很有用
wang wang-1-366
char *line;
while(fgets(line,100,fp)!=NULL){
	sscanf(line,"[^-]-%d-%d",stu[i].name,stu[i].type,stu[i].score);
	i++;
	
}

6.生成格式化的字符串
7.填充字符串

// An highlighted block
int p1[10];
memset(p1,0,10*sizeof(int));//将数组初始化为0

基础代码块

应该掌握一些基础的代码块
只含数字字符的字符串转数字

// An highlighted block
1.
atoi(str);
2.

int sum=0,sign=1;//sign用来表示正负号
if(str[0]=='+'||str[0]=='-') sign=(str[0]=='+')?1:-1;//第一个字符若是正负符号
for(int i=0;str[i]>'0'&&str[i]<'9';i++)
   sum=sum*10+(str[i]-'0');
sum=sum*sign;

遍历两字符串或者母串和子串

// An highlighted block
int i=0;
while(s1[i]!='\0')
   int j=0;
   while(s2[j!='\0']){
   	//进行接下来的操作
   	}

字符串最后的指针(字符串的长度)

// An highlighted block
char *l=p;//l尾指针,p头指针
int len=0
while(*l!='\0'){l++;len++;}//通过判断是否为最后一个字符

字符串的连续分割 (取字符串中一些连续的特殊字符进行处理)

// An highlighted block
char *temp=p;
while(*temp!='\0'){
   chart *temp2=temp;//temp2负责前进,temp负责记住开始位置
   while(*temp2满足的条件&&temp0!='\0')  temp2++;
   //接下来就可以对temp到temp2的字符进行处理
   //如分割单词(temp满足不是空格)、取出数字(temp2满足数字)等
   //完成后temp2两种状态1.或者未‘\0’。2:或者为不满足但不是最后,分两种情况更新temp
   if(*temp2!='\0') temp=temp2+1;
   else temp='\0';
}

统计字符串不用字符的频数
方式很多种,这里选用最基础的采用两个额外数组计数
两个指针,两层遍历,外层用来遍历字符串,内层用来遍历a数组,如当前字符,a数组没有,则加入a,b新元素对应加1;若a中有,则b在a遍历到的位置元素加1

// An highlighted block
//   s 字符串
char a[len],int b[len]//a数组用来记录字符,b数组用来记录相对应的频度
for(int i=0;i<len;i++) b[i]=0;//计数数组初始化为0
int k=0;//用来记录a中元素的个数
a[0]=s[0];b[0]++;k++;//第一个元素肯定是
for(int i=1;i<len;i++){//遍历字符串
	int j=0;//用于遍历a数组
	while(j<k&&s[i]!=a[j]) j++;//查看数组a中是否有,
	if(j==k){//因为j<k跳出则a中没有
		a[j]=s[i];
		b[j]++;k++;
	}
	else b[j]++;

}

特别的,当已经告知只有小写字母时(或只有数字,只有大写字母),则仅仅需要一个数组,此事a数组可以省去,

// An highlighted block
//   s 字符串,设其中只含有小写字母
int b[26]//b数组用来记录字母相对应的频度
for(int i=0;i<26;i++) b[i]=0;//计数数组初始化为0
for(int i=0;i<len;i++){//遍历字符串
	int c=s[i]-'a';//c即为要加的位置
	b[c]++;
}//打印时,只需要将b中不为零的打印就可以

字符串的翻转问题

1.整体翻转
思路:处理方式双指针的方法,两块代码。1:定位到尾指针。2:头尾交换

// An highlighted block
void Verse(char *p){
	char *l=p;
	while(*l!='\0') l++; //定位到尾指针
	char temp;
	while(p!=l){ //交换指针所指的内容
		temp=*p;
		*p=*l;
		*l=temp;
		p++;l--;
	}
}

1.部分翻转
问题:将每个单词翻转 如输入Hello world,输出world Hello
思路:首先将所有字符翻转(dlrow olleH),再顺序的将每个单词翻转(world Hello)。
两块功能:1.翻转的函数改上边的函数,2.区分每个单词;

// An highlighted block
void Verse(char *p,char *l){//改为需要首尾两个参数,不需要再遍历到尾部
	char temp;
	while(p!=l){ //交换指针所指的内容
		temp=*p;
		*p=*l;
		*l=temp;
		p++;l--;
	}
}

void Verse_Word(char *p){
	char *l=p;
	while(*l!='\0') l++; //定位到尾指针
	Verse(p,l); // 所有的字符倒转
	char 
	
	while(*)

}

两字符串对比的问题

1.两字符串的最长公共子串
思路:扫描两串,当前字符相等时,比较后面字符,直到不等,所得串与最长作对比。

// An highlighted block
void MAX_Com_Str(char t[],char s[],char c[]){//求t和s的最长公共串,c来存放
   int s_len=0;int index=0;//最长长度,和最长字符串起始
   int len;
   int i=0,j=0;
   while(s[i]!='\0'){
   		j=0;
   		while(t[j]!='\0'){
   			if(s[i]==t[j])//当前字符相等,则开始求最长
   			{
   				len=1;
   				for(k=1;i+k<strlen(s)&&j+k<strlen(t)&&s[i+k]==t[j+k];k++){
   				//两个字符都没有出界,且相等,(三个条件)
   					len++;
   					}
   				if(len>s_len){  index=i;s_len=len;}//满足则更新最大
   				j+=len;//二串更新
   				}
   			else  j++;
   			
   			}
   		i++;//一串更新
}
for(i=0;i<s_len;i++){//长度
c[i]=s[index+i];
}
c[len]='\0';

}
  • 6
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值