C语言文件中字符串的查找与替换

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C语言文件中字符串的查找与替换相关的知识,希望对你有一定的参考价值。

#include<stdio.h>
#include<conio.h>
#include<string.h>
#include<stdlib.h>

int Count=0;

int findNum(char *str)

int i=0,t1=0;
FILE *p;
char ch;
if((p=fopen("image.gl","rb"))==NULL)

printf("\n打开文件失败\n");
exit(4);

while((ch=fgetc(p))!=EOF)

if(ch==str[t1])
t1++;
else
t1=0;
if(t1>=strlen(str))

printf("找到字符串%s位置为%d\n",str,i-strlen(str)+1);
Count = i-strlen(str)+1;
i=1;
break;

i++;

fclose(p);

if(!i) return 0;
return i;


int main(void)

FILE *in,*out;
char *str1="1234567";
char *str2="abcdef";
int i=0,j=0,t1=0,t2=0;
char ch;
if((t1=findNum(str1))==0)

printf("没有找到字符串%s\n请按任意键退出\n",str1);
return -1;

if((t2=findNum(str2))==0)

printf("没有找到字符串%s\n请按任意键退出\n",str2);
return -2;


if((in=fopen("image.gl","rb"))==NULL)
printf("\n打开文件失败\n");
exit(2);

if((out=fopen("image_new.gl","wb"))==NULL)
printf("\n创建新文件失败\n");
exit(3);


i=0;

/* start copy */
while((ch=getc(in))!=EOF)

if(t1||t2)

if(Count<=80)

if(i<=Count) fputc('0',out);
else fputc(ch,out);

else

if((i>=(Count-80))&&(i<=Count)) fputc('0',out);
else fputc(ch,out);

i++;


fclose(in);
fclose(out);
printf("替换完成!\n任意键关闭!\n");
getch();

问题:目前无法确定是否找到了字符串并且替换,而且生成出的文件始终为381KB,请高手予以调试修改!感谢!
不好意思~~说的不太清楚,找到对应字符串之后将字符串之前的80个字符全部替换为0
文件会比较大,可能会有两三G大~~
高手帮忙看看啊,谢谢~~

  #include<stdio.h>
  #include<conio.h>
  #include<string.h>
  #include<stdlib.h>
  void Substitute(char *pInput, char *pOutput, char *pSrc, char *pDst)
  
  char    *pi, *po, *p;
  int     nSrcLen, nDstLen, nLen;
  // 指向输入字符串的游动指针.
  pi = pInput;
  // 指向输出字符串的游动指针.
  po = pOutput;
  // 计算被替换串和替换串的长度.
  nSrcLen = strlen(pSrc);
  nDstLen = strlen(pDst);
  // 查找pi指向字符串中第一次出现替换串的位置,并返回指针(找不到则返回null).
  p = strstr(pi, pSrc);
  if(p)
  
  // 找到.
  while(p)
  
  //计算被替换串前边字符串的长度.
  nLen = (int)(p - pi);
  // 复制到输出字符串.
  memcpy(po, pi, nLen);
  memcpy(po + nLen, pDst, nDstLen);
  // 跳过被替换串.
  pi = p + nSrcLen;
  // 调整指向输出串的指针位置.
  po = po + nLen + nDstLen;
  // 继续查找.
  p = strstr(pi, pSrc);
  
  // 复制剩余字符串.
  strcpy(po, pi);
  
  else
  
  // 没有找到则原样复制.
  strcpy(po, pi);
  
  
  int main(int ac, char *av[])
  
  if (ac!=5) 
  printf("程序名 要操作的文件 新文件 查找的字符串 替换的字符串\\n");
  printf("示例:test.exe 1.txt 2.txt hello love\\n");
  return 0;
  
  const int MAXSIZES = 100;
  FILE *fpSrc,*fpDes;
  char filename1[20]="1.txt";
  char filename2[20]="2.txt";
  //要求查找的字符串,替换的字符串;
  char ps[]="hello";
  char pd[]="love";
  //求取所查找和替换的字符串的长度;
  int len_src=strlen(av[3]);
  int len_des=strlen(av[4]);
  //定义存储字符串缓冲区;很奇怪的一点是,fgets函数不能将字符串写入动态分配的内存中
  /*char* Src_buf=(char*)(sizeof(char)*MAXSIZES);
  char* Cpy_buf=(char*)(sizeof(char)*MAXSIZES);
  char* Des_buf=(char*)(sizeof(char)*MAXSIZES);*/
  char Src_buf[MAXSIZES] = 0;
  char Cpy_buf[MAXSIZES] = 0;
  char Des_buf[MAXSIZES] = 0;
  //打开文件
  if((fpSrc=fopen(av[1],"r+"))==NULL)
  
  printf("fail to open the file1 !\\n");
  exit(1);
  
  if((fpDes=fopen(av[2],"a+"))==NULL)
  
  printf("fail to open the file2 !\\n");
  exit(1);
  
  //进行循环读取
  while(!feof(fpSrc))//判断文件是否已结束;!feof(fpSrc)
  
  fgets(Src_buf,MAXSIZES,fpSrc);
  Substitute(Src_buf,Des_buf,av[3],av[4]);
  fputs(Des_buf,fpDes);
  printf("%s",Des_buf);
  
  fclose(fpSrc);
  fclose(fpDes);
  system("pause");
  return 0;
  

说明:使用c标准为中的文件I/O函数一般是不推荐的,做为练习可以学习,真正用的最多的是内存文件映射。那要比用I/O函数读来读取方便的多,限制也会更小。
参考技术A 用"rb" open, 用 fread 读, 用 fwrite 写.
记录地点 用 fgetpos.

下面程序例子是按你的原来题意,找目标字串,输出用替代字.直接用文件操作,不开单元存放文件.

输入文件 a.txt 输出文件 tmp.txt

至于你的新要求,给你提示记录地点的方法.你可以rewind(fin),从头一个字一个字读,读一个输出一个,读到的位置等于POS[i]-80时,读80个字但不输出,这就去掉了80个字.
例如找到的POS[]共NN个。
#define buff_size 1024
long int n,n1,n2,i,j,k;
char *buff;
buff=(char*) malloc(buff_size * sizeof(char));
rewind(fin);
for(k=0;k<NN;k++)
if (k==0) n=POS[k]-80; else n=POS[k]-POS[k-1]-80;;
n1 = n / buff_size; n2 = n % buff_size;
if (n1 >0) for (i=0;i<n1;i++)
fread(buff,sizeof(char),buff_size,fin);
fwrite(buff,sizeof(char),buff_size,fout);
;
if (n2 > 0) fread(buff,sizeof(char),n2,fin);
fwrite(buff,sizeof(char),n2,fout);
;
fread(buff,sizeof(char),80,fin);
for (i=0;i<80;i++) buff[i]='0'; buff[80]='\0';
fwrite(buff,sizeof(char),80,fout);
; end for k
这里请自己写 读最后一段,无需改零,读一个字,输出一个字,直到EOF.
-----------------
#include <stdio.h>
#include <stdlib.h>

void main (int argc, char *argv[])

FILE *fin,*fout;
char namein[72]="a.txt";
char nameout[72]="tmp.txt";
char target[120],tidai[120];
char work[120];
int L1,L2,i,k=0;
int numread;
fpos_t pos;
fpos_t POS[100];

printf("Enter target string: ");
scanf("%s",&target[0]);
L1 = strlen(target);
printf("Enter replace string: ");
scanf("%s",&tidai[0]);
L2 = strlen(tidai);

if ( (fin = fopen(namein,"rb") ) == NULL )
printf("\007Cann't open input file: %s ", namein);exit(1);
;

if ( (fout = fopen(nameout,"wb") ) == NULL )
printf("\007Cann't open temp work file: %s ", nameout);exit(1);
;

Lab1:
numread = fread( work, sizeof( char ), L1, fin );
if (numread < L1)
// fwrite( work, sizeof( char ), numread, fout );
goto done;
;
if ( strncmp(work,target,L1) == 0 )
// fwrite( tidai, sizeof( char ), L2, fout );
if( fgetpos( fin, &pos ) != 0 ) perror( "fgetpos error" );
else POS[k] = pos-L1; k=k+1;;

goto Lab1;
;

Lab2:
// fwrite( &work[0], sizeof( char ), 1, fout );
for (i=0;i<L1-1;i++) work[i]=work[i+1];
fread( &work[L1-1], sizeof( char ), 1, fin );
if (feof(fin))
// fwrite( &work[1], sizeof( char ), L1-1, fout );
goto done;
;
if ( strncmp(work,target,L1) == 0 )
// fwrite( tidai, sizeof( char ), L2, fout );
if( fgetpos( fin, &pos ) != 0 ) perror( "fgetpos error" );
else POS[k] = pos-L1; k=k+1;;
goto Lab1;
else goto Lab2;;

// 新述 rewind(fin); 那部分程序语句插在这里,声明放前面

done: fclose(fin);fclose(fout);
printf("output in %s\n",nameout);
for (i=0;i<k;i++)
printf("%ld \n",(long int) POS[i]);

exit(0);
参考技术B 你可以这样写,void replace() /*替换单词*/

char word[max],reword[max],ch;/*word 为被替换单词,reword为替换单词*/
printf("\n======单词替换======\n");
printf("\n请输入欲被替换的单词:");
scanf("%s",&word);
printf("\n共找到%2d 处 ” %s ” \n",wordfind(word),word);
if (!wordfind(word))

printf("\n对不起!不存在该单词!");
getchar();

else

printf("\n该单词替换为:");
scanf("%s",&reword);
printf("\n确定是否要替换为 “ %s ”?(Y/N) : ",reword);
getchar();
scanf("%c",&ch);
if (ch=='y'||ch=='Y')
if (!revisal(pos,strlen(word),reword))
printf("\n修改成功!");



int wordfind(char word[]) /*单词匹配*/

int i=0,s=0,j,k,len,count=0;
char str[max];
len=strlen(psg);
while (i<len) /*寻找单词*/

if ((psg[i]>='a'&&psg[i]<='z')||(psg[i]>='A'&&psg[i]<='Z'))

k=0;
for (j=i;j<len;j++)

if ((psg[j]>='a'&&psg[j]<='z')||(psg[j]>='A'&&psg[j]<='Z'))

str[k]=psg[j]; /*str记录文段中出现的单词*/
k++;

else

i=j+1;
break;


if (!strcmp(str,word)) /*对文段中单词和欲替换单词比较*/

count++; /*若相同,则统计该单词并记录其起始位置*/
pos[s]=i-k-1;
s++;

for (j=0;j<k;j++)
str[j]='\0'; /*初始化字符串str*/

else
i++;

return count;


int revisal(int pos[],int len,char reword[]) /*替换后修改文件*/

int i=0,j=0,k;
if ((fp=fopen(filename,"w"))==NULL) /*打开文件*/

printf("文件打开失败!");
exit(0);

while (i<strlen(psg))

if (pos[j]==i) /*在文件中修改替换单词*/

for (k=0;k<strlen(reword);k++)
fwrite(&reword[k],sizeof(char),1,fp);
i+=len; /*在psg数组中跳过被替换单词*/
j++;

else

fwrite(&psg[i],sizeof(char),1,fp);
i++;


if (fclose(fp)) /*关闭文件*/

printf("关闭文件失败");
exit(0);

getchar();
return 0;
参考技术C #include<iostream>
#include<conio.h>
#include<string>
#include<stdlib.h>
using namespace std;

int Count=0;

/*
*函数名:findNum
*作者:anglecloudy
*描述:如果存在则返回字符串所在的位置,否则返回0,暂不支持文本中存在多个相同的串
* 先用test.txt文本测试,所有的文本操作都是一样的,不管你怎么命名
*/
int findNum(char *str)

FILE *p;
if((p=fopen("test.txt","rb"))==NULL)

printf("\n打开文件失败\n");
return 0;

char buffer[0x1000]; //保存文件
memset(buffer,0,0x1000); //初始化缓存
size_t fileLen=fread(buffer,sizeof(char),0x1000,p); //得到文件内容,
int readLen=strlen(str);
int IsFind=0;

for(int i=0;i<fileLen;i++)

if(strncmp(buffer+i,str,readLen)==0)

IsFind=i;



fclose(p);
return IsFind;


int main(void)

char *str1="1234567";
int t1=0,t2=0;
if((t1=findNum(str1))==0)

printf("没有找到字符串%s\n请按任意键退出\n",str1);
return -1;

else

printf("字符串%s的位置在%d\n",str1,t1);

return 0;


我只是简单的改了一下你的字符串查找这个函数,其它的没写。主要是你的思想不对,对文件的操作一般先定义一个数组,把文件保存起来,然后再操作,多去http://community.csdn.net上面问问,高手多,下班了。88本回答被提问者和网友采纳
参考技术D 给些建议:
1.你需要替换的文件是否很大,如果不大(不超过10M),一次读完它,别一个字节一个字节读,自己给自己找麻烦。(获取文件大小/c里面可以用fseek+ftell获取,然后malloc对应大小的空间,一次fread读完。)
理由:你这个不是要长时间运行的系统,不用考虑内存占用,因为跑完就结束了。

2.如果都在内存里了,直接可以用库函数strstr来查找,比你自己比较方便许多,代码也没这么复杂。

C++实现txt文件中的查找与替换功能

设计一个程序,实现txt文件中的查找与替换功能,要求如下:
在原始文件1.txt中输入一段字符串,运行程序,在输出文件2.txt中实现用空格替换回车的功能。
(这应该是程序的一部分,求大神帮忙补全,如果完整,请帮忙找出错误)

FILE *fp1,*fp2; \\声明文件指针变量名
char del;
int i;
printf("\n1.txt为原始文件.");
printf("2.txt为替换文件.\n");
printf("\n按 ENTER 键继续!\n");
getchar(); \\键盘读入字符
if((fp1=fopen("1.txt","r+"))==NULL) \\打开原始文件1.txt,将其赋给了文件指针fp1,并判断文件指针fp1是否为NULL
printf(" 1.txt 打开失败!\n");
exit(0); \\终止程序

if((fp2=fopen("2.txt","w+"))==NULL) \\打开原始文件2.txt,将其赋给了文件指 针fp2,并判断文件指针fp2是否为NULL
printf(" 2.txt 打开失败!\n");
exit(0); \\终止程序

while((del=fgetc(fp1))!=EOF) \\如果文件fp1读入结束,结束循环
if(del=='\n') \\回车
i=fputc(' ',fp2); \\空格
if(i==-1) printf("写入2.txt失败!\n");

else
i=fputc(del,fp2); \\空格替换回车
if(i==-1) printf("写入2.txt失败!\n");

#include <stdio.h>

#include <string.h>

#include <stdlib.h>

void file_replace(FILE *fp_in,FILE *fp_out,char *src,char *dst)

 char c=fgetc(fp_in);

 char tmp[100];

 int count=0;

 while(c!=EOF)

 

  int pPos=0;

  if(c!=src[pPos]) 

 

   fputc(c,fp_out);

   c=fgetc(fp_in);

   continue;//如果当前字符不相等,继续下一个字符

 

  memset(tmp,0,100);

  while(c==src[pPos]) 

 

   tmp[pPos]=c;

   c=fgetc(fp_in);

   pPos++;//相等的部分跳过

 

  if(src[pPos]=='\\0') 

 

   count++;

   printf("源串已找到!替换%d处\\n",count);

   fputs(dst,fp_out);

   continue;

 

  else

 

   fputs(tmp,fp_out);

   continue;//如果当前字符不相等,继续下一个字符

 

 

 return;

int main()

 char path[100],old_path[100];

 printf("请输入文件路径:\\n");

 gets(path);

 strcpy(old_path,path);

 FILE *fp_in;

 FILE *fp_out;

 fp_in=fopen(path,"rt");

 fp_out=fopen(strcat(path,".bak"),"wt");

 if(!fp_in||!fp_out) 

 

  printf("File open error!");

 

 

 char src[100],dst[100];

 printf("请输入要替换的源串:\\n");

 gets(src);

 printf("请输入要替换的目的串:\\n");

 gets(dst);

 file_replace(fp_in,fp_out,src,dst);

 fclose(fp_in);

 fclose(fp_out);

 char cmd[200]="copy ";

 strcat(cmd,path);

 strcat(cmd," ");

 strcat(cmd,old_path);

 system(cmd);

 memset(cmd,0,200);

 strcat(cmd,"del ");

 strcat(cmd,path);

 system(cmd);


参考技术A

1、打开文件,遍历文件内容然后一个一个匹配查找并替换,最后再重新写入文件当中。
2、例程:

#include <stdio.h>
int main()

FILE *fp;
char filename[100];
printf("请输入文件名:\\n");
gets(filename);
fp=fopen(filename,"r");
char c,x,flag=0;
printf("请输入要查找的字符:\\n");
scanf("%c",&x);
while(fscanf(fp,"%c",&c)!=EOF)

if(c==x)

flag=1;
break;


if(flag==1)
printf("文件中含有字符%c\\n",x);
else
printf("文件中没有字符%c\\n",x);
return 0;

参考技术B  #include <stdio.h>
 #include <stdlib.h>
 int main()
 
  FILE *fp1,*fp2; //声明文件指针变量名
  char del;
  int i;
  printf("\n1.txt为原始文件.");
  printf("2.txt为替换文件.\n");
  printf("\n按 ENTER 键继续!\n");
  getchar(); //键盘读入字符
  if((fp1=fopen("1.txt","r+"))==NULL) //打开原始文件1.txt,将其赋给了文件指针fp1,并判断文件指针fp1是否为NULL
  
  printf(" 1.txt 打开失败!\n");
  exit(0); //终止程序
  
  if((fp2=fopen("2.txt","w+"))==NULL) //打开原始文件2.txt,将其赋给了文件指 针fp2,并判断文件指针fp2是否为NULL
  
  printf(" 2.txt 打开失败!\n");
  exit(0); //终止程序
  
  while((del=fgetc(fp1))!=EOF) //如果文件fp1读入结束,结束循环
  
  if(del=='\n') //回车
  
  i=fputc(' ',fp2); //空格
  if(i==-1) printf("写入2.txt失败!\n");
  
  else
  
  i=fputc(del,fp2); //空格替换回车
  if(i==-1) printf("写入2.txt失败!\n");
  
  
  return 0;
 追问

大神,还是运行不了,再给看看吧。你也运行下吧
....
...
c(35) : error C2018: unknown character '0xa1'
C:\Program Files (x86)\Microsoft Visual Studio\MyProjects\W002M\W002M.c(35) : error C2018: unknown character '0xa1'
执行 cl.exe 时出错.

W002M.exe - 1 error(s), 0 warning(s)

追答

#include
#include
int main()

FILE *fp1,*fp2; //声明文件指针变量名
char del;
int i;
printf("\n1.txt为原始文件.");
printf("2.txt为替换文件.\n");
printf("\n按 ENTER 键继续!\n");
getchar(); //键盘读入字符
if((fp1=fopen("1.txt","r+"))==NULL) //打开原始文件1.txt,将其赋给了文件指针fp1,并判断文件指针fp1是否为NULL

printf(" 1.txt 打开失败!\n");
exit(0); //终止程序

if((fp2=fopen("2.txt","w+"))==NULL) //打开原始文件2.txt,将其赋给了文件指 针fp2,并判断文件指针fp2是否为NULL

printf(" 2.txt 打开失败!\n");
exit(0); //终止程序

while((del=fgetc(fp1))!=EOF) //如果文件fp1读入结束,结束循环

if(del=='\n') //回车

i=fputc(' ',fp2); //空格
if(i==-1) printf("写入2.txt失败!\n");

else

i=fputc(del,fp2); //空格替换回车
if(i==-1) printf("写入2.txt失败!\n");


return 0;


代码行末尾有空格,现在应该可以了

参考技术C 先产生一个临时文件,然后通过fgets按行读取原始文件并用sscanf查找特定字串,找到之后直接替换,然后用fputs写入 临时文件,当原文件遍历完时,删除原文件,然后将临时文件命名和原始文件相同即可,或者直接用fscanf即可 参考技术D 很简单,使用正则表达式即可

以上是关于C语言文件中字符串的查找与替换的主要内容,如果未能解决你的问题,请参考以下文章

c语言编程替换文件中字符串

c语言:文件操作与字符处理

怎样在emacs中进行多文件字符串查找/替换

C++编程,查找字符串子串并替换。

用C/C++实现字符串的创建,并进行查找与替换

C语言 文件方面 段错误 核心已转储 以及字符串查找删除的问题