字符串在任何语言里面都是举足轻重的, c语言作为比较古老的语言, 字符串操作的方法不是非常多, 一些高级语言才有的字符串方法,也可以自己手动实现,先说字符串的创建, 可以使用C风格创建一个字符串,或者使用数组字符串, 每一个字符串占用一个字节, 字符串的最后结束符默认为0, 系统默认会添加结束符, 所以字符串的字节长度为:所有的字符长度+1:
#include <stdio.h>
int main() {
//定义常量,不需要定义长度
//字符串默认是以0作为最后一个字符结束的;
char str[] = "abcd";
//const char* str = "a"; 这种方式创建的字符串就是指针
//char* str[] = "abcdefg";
printf("%d\n",(int)sizeof(str));
for(int i=0 ;str[i]!=0 ; i++) {
printf("%c\n",str[i]);
}
return 0;
}
要获取字符串的长度可以使用:sizeof("abcd"); 当我们使用指针指向一个字符串的时候,怎么获取字符串的长度呢? 系统没有定义获取字符串指针长度的方法, 自己实现一个呗:
#include <stdio.h>
int getLen(char *p) {
int i=0;
while(p[i]!=0){
i++;
}
return i;
}
int main() {
char str[] = "12345";
int len = getLen(str);
printf("the string %s length is %d\n", str, len);
return 0;
}
在<string.h>中有定义了一个字符串复制strcpy方法, 可以自己实现:
#include <stdio.h>
void strcpy(char *p, char *p1) {
int i=0;
while(p1[i]!=0) {
p[i] = p1[i];
i++;
};
//再给最后一个设置一下结束符;
p[i] = 0;
}
int main() {
char str[] = "12345";
char str1[5];
//复制字符串;
strcpy(str1, str);
printf("the string %s ", str1);
return 0;
}
在<string.h>中也定义了strcmp方法,作为字符串的比较,可以这么实现:
#include <stdio.h>
int strcmp(const char* p,const char* p1) {
if(*p<*p1) {
return -1;
}else if( *p>*p1) {
return 1;
}else {
return 0;
}
}
int main() {
char str[]= "a";
char str1[]= "a";
int val = strcmp(str, str1);
printf("the compare value is %d\n", val);
return 0;
}
字符串删除的方法呢, 也可以
#include <stdio.h>
#include <stdlib.h>
int getLen(char *p) {
int i=0;
while(p[i]!=0){
i++;
}
return i;
}
char* strdel(char* p, int index) {
char *str = (char *)malloc(getLen(p)-1);
int i=0;
while(p[i]) {
if(i<index) {
str[i] = p[i];
}else{
str[i] = p[i+1];
}
i++;
}
str[i] = 0;
return str;
}
int main() {
char str[]= "abcdefg";
char *p = strdel(str,2);
printf("the result value is %s\n", p);
return 0;
}
也可以手动实现一个从字符串的任意位置添加字符串的方法,这个实现起来有点麻烦:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
int getLen(char *p) {
int i=0;
while(p[i]!=0){
i++;
}
return i;
}
//实现从任意位置插入字符串;
char* insert(char *p ,int index ,char *p1) {
//复制一个p, 然后把p的index位往后面一动p1.length位, 接着把p1复制过去;
char* result;
//申请空间
int sourceLen = getLen(p1);
int destLen = getLen(p);
int len = destLen+sourceLen+1;//要加一位作为结束字符
result = (char*)malloc(len);
//复制一个result
strcpy(result, p);
//把result重新移动
int count = destLen - sourceLen;
for(int i=destLen; i>=index-1; i--) {
result[sourceLen+i]= result[i];
}
for(int i=0 ;i<sourceLen; i++) {
result[i+index] = p1[i];
}
//返回
return result;
}
int main() {
char str[] = "123456789";
char str1[] = "abcd";
char* p = insert(str,2,str1);
printf("the string %s\n", p);
return 0;
}
字符串分割的方法也可以自己实现, 但是需要自己定义一个结构体,否者不好弄:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
//定义一个结构体
struct link{
char str[10];
link* next;
};
int getLen(char *p) {
int i=0;
while(p[i]!=0){
i++;
}
return i;
}
void copyStr(char *p ,char* p1, int index) {
int i = 0;
while(i!=index) {
p[i] = p1[i];
i++;
}
p[i] = 0;
}
void linkadd(link* l, char *p) {
link* curr = l;
while(curr->next) {
curr = curr->next;
};
link* newl = (link *)malloc(sizeof(link));
strcpy(newl->str, p);
newl->next = NULL;
curr->next = newl;
}
link* sp(link* l,char* p, char s) {
int i, index = 0, j=0;
char chars[10];
int len = getLen(p);
//创建一个有头链表;
for(i=0; i<len; i++) {
if( p[i] == s & j!=0) {
//添加链表
char* c = (char*)malloc(j);
copyStr(c, chars, j);
linkadd(l, c);
//重新清空chars和j;
strcpy(chars, "");
j=0;
}else if( p[i] != s ){
//循环获取字符到临时数组chars;
chars[j] = p[i];
j++;
}
}
char* c = (char*)malloc(j);
copyStr(c, chars, j);
linkadd(l, c);
return l;
}
int main() {
link l={"no", NULL};
char str[]= "ccadeafgaaaaabcd";
link* p =sp(&l, str, 'a');
while(p) {
printf("split: %s\n",p->str);
p = p->next;
}
return 0;
}
有了结构体,最后就可以把结构体转换为数组, 也要自己实现咯;
下面复习时间对象, 引用time.h,然后time(NULL) :
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
int main() {
time_t now = time(NULL);
printf("%d\n", (int)now);
tm info = *localtime(&now);
printf("%d\n", info.tm_year);
printf("%d\n", info.tm_mon);
printf("%d\n", info.tm_mday);
printf("%d\n", info.tm_hour);
printf("%d\n", info.tm_min);
printf("%d\n", info.tm_sec);
return 0;
}
随机数的使用:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
int main() {
srand(time(NULL));
int n = rand();
printf("%d\n", n);
return 0;
}
文件读取:
#include <stdio.h>
#include <stdlib.h>
int main() {
FILE* fp;
fp = fopen("fop.cpp","r");
if(fp==NULL) {
printf("error to open!\n");
}
char buff[1];
while(1) {
fread(buff,1,1,fp);
if(feof(fp)) {
break;
};
printf("%c", *buff);
}
fclose(fp);
return 0;
}
缓冲区buff的大小可以设置为更大,比如4个:
#include <stdio.h>
#include <stdlib.h>
int main() {
FILE* fp;
fp = fopen("fop.cpp","r");
if(fp==NULL) {
printf("error to open!\n");
}
char buff[4];
while(1) {
fread(buff,1,4,fp);
if(feof(fp)) {
break;
};
printf("%c%c%c%c", buff[0], buff[1], buff[2], buff[3]);
}
fclose(fp);
return 0;
}
#include <stdio.h>
#include <stdlib.h>
int main() {
FILE* fp;
fp = fopen("fop.cpp","rb");
if(fp==NULL) {
printf("error to open!\n");
}
char buff[4];
//需要手动把buff的最后一个字符变为结束字符,方便系统直接读取字符串
buff[3] = 0;
while(1) {
int n = fread(buff,1,3,fp);
if(feof(fp)) {
break;
};
//printf("%c%c%c%c", buff[0], buff[1], buff[2], buff[3]);
printf("%s", buff);
//printf("%d\n", n);
}
fclose(fp);
return 0;
}
文件读取:
#include <stdio.h>
#include <stdlib.h>
int main() {
FILE* fp;
fp = fopen("fop.cpp","r");
while(1) {
int c = fgetc(fp);
if(feof(fp)) {
break;
};
printf("%c", c);
}
fclose(fp);
return 0;
}
使用fseek,访问文件的指定位置, 这样的话如果是utf-8这种不固定长度的情况下, 如何判断要访问哪个字节?
#include <stdio.h>
#include <stdlib.h>
int main() {
FILE* fp;
fp = fopen("fop.cpp","rb");
if(fp==NULL) {
printf("error to open!\n");
}
char buf[1];
fseek(fp, 1, SEEK_SET);
while(1) {
if(feof(fp)){
break;
}
fread(buf, 1, 1, fp);
printf("%c", buf[0]);
}
fclose(fp);
return 0;
}
文件写入:
#include <stdio.h>
#include <stdlib.h>
int main() {
FILE* fp;
char str[10] = "abcdefg";
////打开或者创建
fp = fopen("txt.txt","wb");
fwrite(str, 1 ,sizeof(str), fp);
fclose(fp);
return 0;
}
EOF
done
天道酬勤