C++批量修改文件系统

C++批量修改文件系统

前情提要:从bilibili下了鸟的歌,不晓得发生甚么事了,居然下载了两遍。
哇我好蓝瘦啊,难道我要一个个改吗,有200多个诶!
在这里插入图片描述
在这里插入图片描述
我寻思可以用C++做一个面向过程的程序啊
于是在此感谢C++调用文件函数的教程:
原文链接:https://blog.csdn.net/u012500825/article/details/41947013

成品介绍:
1.可以读取文件路径下所有文件的文件名,以字符串的形式输出(getFiles函数)
2.可以匹配含有特定字符的文件,*.mp3
3.可以对被匹配的文件进行重命名操作

原理与修改意见:本质就是递归,如果是文件夹就下一层,否则就遍历所有的文件
在else里面就是直接对某个文件fileinfo进行操作,如果要改造的话就在这里删改

	do
	{	//如果是目录,迭代之
		if((fileinfo.attrib &  _A_SUBDIR))
		{
			if(strcmp(fileinfo.name,".") != 0  &&  strcmp(fileinfo.name,"..") != 0)
				getFiles( p.assign(path).append("\\").append(fileinfo.name), files );
			//p.assign(path).append("\\").append(fileinfo.name) 
			//意思是 给p赋值path 附加\ 再附加当前文件的名字  
		}
		else
		{
			rename(p.assign(path).append("\\").append(fileinfo.name).c_str(), new_name.c_str());//真实修改
		}
	}while(_findnext(hFile, &fileinfo)  == 0);//文件夹里的文件未被完全遍历 

改造成品:可以直接使用exe

#include <io.h>
#include <iostream>
#include <vector>
#include <string>
#include <string.h>
#include <sstream> 
using namespace std;
/*
两个特殊变量time_t(long int), _fsize_t(unsigned)
和常量宏_MAX_FNAME表文件名的最大长度
包括下面这个结构体都在头文件被定义
struct _finddata_t
{
     unsigned attrib;//表示文件的属性
     
     //_A_ARCH(存档)、_A_HIDDEN(隐藏)、_A_NORMAL(正常)、_A_RDONLY(只读)、_A_SUBDIR(文件夹)、_A_SYSTEM(系统)。
	 //这些都是在<io.h>中定义的宏,可以直接使用,而本身的意义其实是一个无符号整型(只不过这个整型应该是2的几次幂,从而保证只有一位为1,而其他位为0)。
	 //既然是位表示,那么当一个文件有多个属性时,它往往是通过位或的方式,来得到几个属性的综合。例如只读+隐藏+系统属性,应该为:_A_HIDDEN | _A_RDONLY | _A_SYSTEM 。
	 
     time_t time_create;/存储文件创建时间
     time_t time_access;//文件最后一次被访问的时间。
     time_t time_write;//文件最后一次被修改的时间。
     _fsize_t size;//文件的大小,即字节数
     char name[_MAX_FNAME];
};*/
void getFiles(string path, vector<string>& files )
{
	//文件句柄
	long  hFile = 0;
	//文件信息
	struct _finddata_t fileinfo;
	string p;
	/*
		long _findfirst( char *filespec, struct _finddata_t *fileinfo );
		如果查找成功的话,将返回一个long型的唯一的查找用的句柄(一个唯一编号)
		这个句柄将在_findnext函数中被使用。若失败,则返回-1。
	*/
	if((hFile = _findfirst(p.assign(path).append("\\*").c_str(),&fileinfo)) !=  -1)
	{
		do
		{	//如果是目录,迭代之
			if((fileinfo.attrib &  _A_SUBDIR))
			{
				if(strcmp(fileinfo.name,".") != 0  &&  strcmp(fileinfo.name,"..") != 0)
					getFiles( p.assign(path).append("\\").append(fileinfo.name), files );
				//p.assign(path).append("\\").append(fileinfo.name) 
				//意思是 给p赋值path 附加\ 再附加当前文件的名字  
			}
			else
			{//如果不是,加入列表
				files.push_back(p.assign(path).append("\\").append(fileinfo.name) );
			}
		}while(_findnext(hFile, &fileinfo)  == 0);//文件夹里的文件未被完全遍历 
		_findclose(hFile);
	}
}


string C,behind;
int next[110];
bool check(string tex){
	int n=tex.size(),m=C.size(),l=behind.size()-1;
	for(int i=n-1;l>=0;i--){//判断后缀名 
		if(behind[l]!=tex[i]) return false;
		l--;
	}//一个纯粹的KMP匹配
	int i=-1,j=-1,ans=0;
	while(i<n-1)
	{
		while(j>-1 && tex[i+1]!=C[j+1]) j=next[j];
		if(tex[i+1]==C[j+1])
		{
			j++;
			if(j==m-1) { ans++; j=next[j]; }
		}i++;
	}return ans>0;
}


string replace;
void reNameFiles(string path,int flag)//本函数的代码含义请看上面getFiles函数
{
    long hFile = 0;
    struct _finddata_t fileinfo;
    static int i=1;
    string p,s;
    if((hFile = _findfirst(p.assign(path).append("\\*").c_str(),&fileinfo)) !=  -1){
        do{
            if((fileinfo.attrib &  _A_SUBDIR)){
                if(strcmp(fileinfo.name,".") != 0  &&  strcmp(fileinfo.name,"..") != 0)
                    reNameFiles( p.assign(path).append("\\").append(fileinfo.name),flag);
            }
            else{
				s=fileinfo.name;
				if(check(s)){//筛选
					stringstream ss;ss<<i;i++;
	                string new_name = p.assign(path).append("\\")+replace+string(ss.str()+behind);//全部附上SB方便删除 
					if(flag==1) cout<<s<<endl;//输出原文件名
					if(flag==2)	cout<<new_name<<endl;//输出改后文件名
					if(flag==3) rename(p.assign(path).append("\\").append(fileinfo.name).c_str(), new_name.c_str());//真实修改
				}
            }
        }
        while(_findnext(hFile, &fileinfo)  == 0);
        _findclose(hFile);
    }
}
int main()
{	
	cout<<"请输入路径:"<<endl;
	char filePath[10010];
	//char  filePath*= "E:\\(置顶)信息学\\(置顶) 安装包 && 杂项\\bilibili";
	//或输入E:\(置顶)信息学\(置顶) 安装包 && 杂项\bilibili
	cin.getline(filePath,1000);
	/*vector<string> files;
	getFiles(filePath, files);
	int size = files.size();
	for (int i = 0;i < size;i++) cout<<files[i].c_str()<<endl;
	cout<<"已获取该路径下的所有文件"<<endl;*/
	//==============================================================================
	cout<<"\n请输入文件后缀:示例:.mp3" <<endl;
	cin>>behind;
	cout<<"\n请输入筛选条件(字符串匹配):示例:(1)" <<endl;
	cin>>C;int m=C.size();next[0]=-1;//KMP预处理
	for(int i=0,j=-1;i<m-1;i++)
	{
		while(j>-1 && C[i+1]!=C[j+1]) j=next[j];
		if(C[i+1]==C[j+1]) j++;
		next[i+1]=j;//要么是0,要么继承后缀 
	}
	cout<<"请确认您即将更改的文件:"<<endl; 
	reNameFiles(filePath,1);
	
	//==============================================================================
	cout<<"\n请输入改名标示字符串:示例:SB" <<endl;
	cout<<"它们即将被改为:"<<endl; 
	cin>>replace;
	reNameFiles(filePath,2);
	
	//==============================================================================
	cout<<"\n确认更改(y/n):"<<endl; 
	char p;cin>>p;
	if(p=='y') reNameFiles(filePath,3);
	return 0;
}

成品效果如下:
在这里插入图片描述

背景故事的后续:

在这里插入图片描述
有空我用Qt做一个 [doge]

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值