字符串的基本操作
字符串数组初始化
int main()
{
//1 大{}号法 初始化列表
//数组初始化有2种方法 默认元素个数、指定元素个数
char buf1[] = {'a', 'b', 'c', 'd', 'e'}; //若没有指定长度,默认不分配零
//若指定长度,不够报错;buf长度多于初始化个数,会自动补充零
char buf2[6] = {'a', 'b', 'c', 'd', 'e'};
char buf3[6] = {'a', 'b', 'c', 'd', 'e'};
//char buf4[5] = {'a', 'b', 'c', 'd', 'e'};
printf("buf3:%s", buf3);
system("pause");
}
在C语言中使用字符数组来模拟字符串,C语言中的字符串是以'\0'结束的字符数组,C语言中的字符串可以分配于栈空间,堆空间或者只读存储区。
int main()
{
//1 用字符串来初始化数组
char buf2[] = {'a', 'b','c','d','\0'};
//2 字符串常量初始化一个字符数组
char buf3[] = {"abcde"}; //结论:会补充零
char buf4[] = "abcde";
char buf5[100] = "abcde";
printf(" strlen(buf5) :%d \n", strlen(buf5));
printf(" sizeof(buf4) :%d \n", sizeof(buf5));
printf(" sizeof(buf4) :%d \n", sizeof(buf4));
}
strlen()求字符串的长度,注意字符串的长度不包含\0
sizeof(类型)字符串的大小,包括\0;
数组法和指针法操作字符串
字符数组名,就是一个常量指针,代表了字符数组首元素的地址,不代表整个数组。
int main()
{
int i = 0;
char buf[100] = "abcde";
char *p = NULL;
//下标法
for(i = 0;i < 100;i++)
{
printf("%c",buf[i]);
}
printf("\n");
//指针法
for(i = 0;i < 100;i++)
{
printf("%c",*(buf5+i));
}
printf("\n");
//指针法
p = buf;
for(i = 0;i < 100;i++)
{
printf("%c",*(p+i));
}
printf("\n");
}
字符串相关一级指针内存模型
void main()
{
char buf[20]= "aaaa";
char buf2[] = "bbbb";
char *p1 = "111111";
char *p2 = malloc(100); strcpy(p2, "3333");
system("pause");
return ;
}
项目开发字符串模型
strstr-whiledowhile模型:
strstr-whiledowhile模型用于在母字符串中查找符合特征的子字符串。
c语言库提供了strstr函数,strstr函数用于判断母字符串中是否包含子字符串,包含的话返回子字符串的位置指针,不包含的话返回NULL。
可以用strstr函数+while模型或者 strstr函数+dowhile模型实现:
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
int main()
{
int ncount = 0;
char *p = "abcd156445abcd456444abcd46844564abcd";
while (p = strstr(p, "abcd"))//指针p指向a
{
ncount++;
p = p + strlen("abcd");
if (*p == '\0')
{
break;
}
}
printf("字符串中出现abcd的次数: %d \n", ncount); //运行可得4
system("pause");
return 0;
}
两头堵模型:去掉字符串两头的空格,作为新的字符串进行输出
创建一个字符型数组,用数组去接收去除空格后的字符串:
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <ctype.h>
int trimSpace(char*str, char*newstr)
{
char* p = str; //不要直接修改形参指针,用一个临时变量去接收它的值,修改临时变量
int count = 0;
if (str == NULL || newstr == NULL)
{
return 0;
}
int i = 0;
int j = strlen(p) - 1;
//是空白符就往后走,直到找到第一个不是空白字符的字符
while (isspace(p[i]) && p[i] != '\0')
{
i++;
}
//是空白符就往前走,直到找到第一个不是空白字符的字符
while (isspace(p[j]) && p[j] != '\0')
{
j--;
}
count = j - i + 1; //计算去除二边空白字符后的长度
strncpy(newstr, str + i, count); //从str的第i个开始,拷贝count个字符到newstr
newstr[count] = '\0'; //别忘了在newstr后面加字符串结束符 '\0'
return 1;
}
int main(void)
{
char *p = " abcd "; //字符串的首尾都有空格
char arrstr[128]; //足以包含去除空格后的字符串就可以
trimSpace(p, arrstr);
printf("字符串: %s \n", arrstr);
system("pause");
return;
}
直接修改原字符串,把空格删除 (这样做的前提是char* 指针所指向的内存空间必须可以被修改才行)
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <ctype.h>
//这个函数直接修改str,所以必须保证传入的字符串str指向的内存空间是可写的
//通过内存四区知道:char *p = " abcd ";这样字符串会存在常量区,是不可修改的
//char buf[128]; 这样字符串buf存在栈区,可以修改,所以在调用trimSpace时可以用char数组调用
int trimSpace(char*str)
{
char* p = str; //不要直接修改形参指针,用一个临时变量去接收它的值,修改临时变量
int count = 0;
if (str == NULL)
{
return 0;
}
int i = 0;
int j = strlen(p) - 1;
//是空白符就往后走,直到找到第一个不是空白字符的字符
while (isspace(p[i]) && p[i] != '\0')
{
i++;
}
//是空白符就往前走,直到找到第一个不是空白字符的字符
while (isspace(p[j]) && p[j] != '\0')
{
j--;
}
count = j - i + 1; //计算去除二边空白字符后的长度
strncpy(str, str + i, count);//直接修改str, 从str的第i个开始,拷贝count个字符到str
str[count] = '\0'; //别忘了在newstr后面加字符串结束符 '\0'
return 1;
}
int main(void)
{
char buf[] = " abcd "; //字符串的首尾都有空格
trimSpace(buf);
printf("字符串: %s \n", buf);
system("pause");
return;
}
字符串反转模型
指针二头堵模型。 二个指针p1,p2 分别指向字符串的开头和结尾,然后依次交换字符的值。
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
int inverse(char *str1)
{
int length = 0;
char *p1 = NULL;
char *p2 = NULL;
if (str1 == NULL)
{
return -1;
}
length = strlen(str1);
p1 = str1; //指针指向字符串的开头;
p2 = str1 + (length - 1); //指针指向字符串的最后一个;
while (p1 < p2)
{
char c = *p1;
*p1 = *p2;
*p2 = c;
++p1;
--p2;
}
return 0;
}
int main(void)
{
//数组内存分配在栈上,可以修改。 如果用指针声明字符串的话,字符串声明在常量区,内存不可修改,程序会报错。
char buf[] = "abcdefg"; //buf[]
inverse(buf);
printf("buf:%s\n", buf);
system("pause");
return 0;
}
利用栈进行递归逆序。
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
int inverse_stack(char *str1, char *buf)
{
if (str1 == NULL || buf == NULL) //递归结束的异常条件
{
return;
}
if (*str1 == '\0') //递归结束的正常条件
{
return;
}
inverse_stack(str1 + 1, buf);
strncat(buf, str1, 1); //到'\0'时递归结束, '\0'前一个字符为g, 然后是c, b, a。
}
int main(void)
{
char buf[] = "abcg";
char g_buf[1024] = { 0 };
inverse_stack(buf, g_buf);
printf("%s", g_buf);
system("pause");
return 0;
}