python实现文件(夹)剪切

自己的需求是这样的:

有a和b两个目录,a目录下的文件(夹)要剪切到b目录下;我用下面这种形式来表达需求,不然说得比较乱。

需求如下:
a目录
    1.文件:
        1)是日志文件:
           (1)文件大小<20m:
                跳过
           (2)日志文件>=20m:
                复制名加上当天日期,然后剪切到b中(记录到日志文件中)
        2)不是日志文件:
           (1)不在b中:
                直接剪切到b中(记录到日志文件中)
           (2)在b中:
                Name = Name + ’_’ ; 然后剪切到b中(记录到日志文件中)
    2.文件夹:
        1)文件夹不在b中:
   	       直接剪切到b中(记录到日志文件中)
        2)文件夹在b里面:
           (1)文件夹内的文件(夹)也在b目录相同文件夹中:
                命名方式同上:Name = Name + ’_’ ;然后剪切(记录到日志文件中)
           (2)文件夹内的文件(夹)不在b目录相同文件夹中:
                直接剪切所有文件(夹)(记录到日志文件中)
b目录
    1.文件
    2.文件夹

自己的实现步骤如下:版本一

#coding:utf-8
'''
    一个剪切脚本
    版本一:实现递归列出多有文件
'''

import os
import shutil
class Shear():

    def __init__(self):
        #源目录
        self.src = "C:\\Users\\LZH\\Documents\\upupoo\\Docker\\config\\文件夹\\python练习\\shear\\a\\"
        #目标目录
        self.dest = "C:\\Users\\LZH\\Documents\\upupoo\\Docker\\config\\文件夹\\python练习\\shear\\b\\"

    def start_shear(self,a_filepath):
        for a_item in os.listdir(a_filepath):                           #遍历源目录下的所有文件
            a_absolute_path = os.path.join(a_filepath,a_item)           #新的目录为传入目录+传入目录里面的文件夹名称
            is_file = os.path.isfile(a_absolute_path)                   #文件赋给 is_file
            is_dir = os.path.isdir(a_absolute_path)                     #目录赋给 is_dir
            if is_file:
                if a_item =="数据传输日志.log":
                    pass
                else:
                    print(a_item)
            elif is_dir:
                if a_item == "回复文件":
                    pass
                elif a_item == "已导入数据库":
                    pass
                else:
                    print("目录为--%s--的有以下文件:"% a_item)
                    shear.start_shear(a_absolute_path)

if __name__ == "__main__":
    shear = Shear()
    shear.start_shear(shear.src)

版本二

#coding:utf-8
'''
    一个文件移动脚本
    版本一:实现递归列出多有文件
    版本二:实现源目录和目的目录的文件移动
'''

import os
import shutil
class Shear():

    def __init__(self):
        #源目录
        self.src = "C:\\Users\\LZH\\Documents\\upupoo\\Docker\\config\\文件夹\\python练习\\shear\\a\\"
        #目标目录
        self.dest = "C:\\Users\\LZH\\Documents\\upupoo\\Docker\\config\\文件夹\\python练习\\shear\\b\\"

    def start_shear(self,a_filepath):
        for a_item in os.listdir(a_filepath):                             #遍历源目录下的所有文件
            a_absolute_path = os.path.join(a_filepath,a_item)             #新的目录为传入目录+传入目录里面的文件夹名称
            is_a_file = os.path.isfile(a_absolute_path)                   #文件赋给 is_file
            is_a_dir = os.path.isdir(a_absolute_path)                     #目录赋给 is_dir
            if is_a_file:                                                 #self.src 里是文件的话处理条件如下:
                if a_item =="数据传输日志.log":
                    pass
                elif a_item in os.listdir(self.dest):                     #如果该文件已经存在于目的目录中,则不操作
                    renamef = a_item.split('.')                           #将文件名及后缀分开
                    #print(rename)
                    os.rename(self.src+a_item, self.src+renamef[0]+"_."+renamef[1])   #若目的目录存在该目录,则修改名字,后加“_”
                else:
                    shutil.move(self.src+a_item, self.dest)               #shutil.move(full_path,destpath) 这里移动文件的源文件要完全路径,否则会报找不到文件的错
                    #os.rename(a_item,self.dest)
            elif is_a_dir:                                                #self.src 里是目录的话处理条件如下:
                if a_item == "回复文件备份" or a_item == "已导入数据库":      #目录名为指定目录名时则不操作
                    pass
                else:
                    #print(a_absolute_path)
                    os.chdir(a_absolute_path)                             #更改目录为src里的每个目录

                    if a_item not in os.listdir(self.dest):               #判断src里面的每一个目录是否在dest里,不在则执行
                        os.makedirs(self.dest+a_item)                     #在dest中创建和src中一样的目录
                    else:
                        mk = self.dest+a_item
                        for ch_item in os.listdir(a_absolute_path):       #存在则遍历src中每个目录里的所有文件
                            if ch_item not in os.listdir(mk):             #文件若不在上一次执行创建的目录中,则移动该文件到新创建的目录中
                                if ch_item == "已导入数据库" or ch_item =="回盘文件":  #文件夹中存在该名称目录则跳过 ;否 则移动
                                    pass
                                else:
                                    shutil.move(ch_item, mk)
                            else:
                                #print("文件已存在,无法移动文件: %s" % ch_item)   #若新创建的目录中已经包含该文件,则提示无法移动
                                if os.path.isdir(self.src+a_item+"\\"+ch_item):     #当目的目录内文件夹有该文件夹时
                                    os.rename(self.src + a_item + "\\" + ch_item,self.src + a_item + "\\" + ch_item + "_")#则修改文件名+“_”,在第二次执行中移动文件,若还存在,则重复前面步骤,直至移动到目的目录
                                else:                                               #目录下为文件时则操作如下
                                    renamed = ch_item.split('.')
                                    os.rename(self.src+a_item+"\\"+ch_item, self.src+a_item+"\\"+renamed[0]+"_."+renamed[1])


if __name__ == "__main__":
    shear = Shear()
    shear.start_shear(shear.src)

版本三:

#coding:utf-8
'''
    一个文件移动脚本
    版本一:实现递归列出多有文件
    版本二:实现源目录和目的目录的文件移动
    版本三:实现日志记录及日志备份
'''

import os
import shutil
from datetime import datetime
class Shear():

    def __init__(self):
        #源目录
        self.src = "C:\\Users\\LZH\\Documents\\upupoo\\Docker\\config\\文件夹\\python练习\\shear\\a\\"
        #目标目录
        self.dest = "C:\\Users\\LZH\\Documents\\upupoo\\Docker\\config\\文件夹\\python练习\\shear\\b\\"
    '''文件(夹)移动部分'''
    def start_shear(self,a_filepath):
        for a_item in os.listdir(a_filepath):                             #遍历源目录下的所有文件
            a_absolute_path = os.path.join(a_filepath,a_item)             #新的目录为传入目录+传入目录里面的文件夹名称
            is_a_file = os.path.isfile(a_absolute_path)                   #文件赋给 is_file
            is_a_dir = os.path.isdir(a_absolute_path)                     #目录赋给 is_dir
            if is_a_file:                                                 #self.src 里是文件的话处理条件如下:
                if a_item == "数据传输日志.log":
                    shear.back_log(self.src+a_item)                       #进入日志文件备份判断程序
                elif a_item in os.listdir(self.dest):                     #如果该文件已经存在于目的目录中,则不操作
                    renamef = a_item.split('.')                           #将文件名及后缀分开
                    #print(rename)
                    os.rename(self.src+a_item, self.src+renamef[0]+"_."+renamef[1])   #若目的目录存在该目录,则修改名字,后加“_”
                else:
                    asize = round(os.path.getsize(self.src+a_item)/1024, 2) #os.path.getsize获取文件大小,round()函数取值范围:小数点后两位
                    shutil.move(self.src+a_item, self.dest)                 #shutil.move(full_path,destpath) 这里移动文件的源文件要完全路径,否则会报找不到文件的错
                    shear.log(a_item, self.dest, asize, '源目录中')
                    #os.rename(a_item,self.dest)
            elif is_a_dir:                                                #self.src 里是目录的话处理条件如下:
                if a_item == "回复文件备份" or a_item == "已导入数据库":     #目录名为指定目录名时则不操作
                    pass
                else:
                    #print(a_absolute_path)
                    os.chdir(a_absolute_path)                             #更改目录为src里的每个目录

                    if a_item not in os.listdir(self.dest):               #判断src里面的每一个目录是否在dest里,不在则执行
                        os.makedirs(self.dest+a_item)                     #在dest中创建和src中一样的目录
                    else:
                        mk = self.dest+a_item
                        for ch_item in os.listdir(a_absolute_path):       #存在则遍历src中每个目录里的所有文件
                            if ch_item not in os.listdir(mk):             #文件若不在上一次执行创建的目录中,则移动该文件到新创建的目录中
                                if ch_item == "已导入数据库" or ch_item =="回盘文件":  #文件夹中存在该名称目录则跳过 ;否 则移动
                                    pass
                                else:
                                    asize = round(os.path.getsize(ch_item)/1024,2)  #os.path.getsize获取文件大小,round()函数取值范围:小数点后两位
                                    shutil.move(ch_item, mk)
                                    shear.log(ch_item, mk, asize, a_item)
                            else:
                                #print("文件已存在,无法移动文件: %s" % ch_item)       #若新创建的目录中已经包含该文件,则提示无法移动
                                if os.path.isdir(self.src+a_item+"\\"+ch_item):     #当目的目录内文件夹有该文件夹时
                                    os.rename(self.src + a_item + "\\" + ch_item,self.src + a_item + "\\" + ch_item + "_")#则修改文件名+“_”,在第二次执行中移动文件,若还存在,则重复前面步骤,直至移动到目的目录
                                else:                                               #目录下为文件时则操作如下
                                    renamed = ch_item.split('.')
                                    os.rename(self.src+a_item+"\\"+ch_item, self.src+a_item+"\\"+renamed[0]+"_."+renamed[1])
    '''记录日志部分'''
    def log(self, data, dest, size, bankname):                                      #文件名;目的目录;大小;银行名称
        record = open(self.src+"数据传输日志.log", 'a')
        record.write("%s-*********-" % datetime.now().strftime('%Y-%m-%d : %H:%M')+"来源:%s" % bankname+"\t文件:%s" % data +"\t大小:%sk" % size +"\t移动到:%s" % dest +"\n")
    '''日志文件备份'''
    def back_log(self,log_file):
        log_size = round(os.path.getsize(log_file)/(1024*1024),1)
        if log_size >= 20:                                                          #若日志文件超过20m,则备份文件
            shutil.copyfile(self.src+"数据传输日志.log",self.dest+"数据传输日志%s.log" % datetime.now().strftime('%Y-%m-%d') )
        else:
            pass

if __name__ == "__main__":
    shear = Shear()
    shear.start_shear(shear.src)

到此为止基本功能都实现了,就是感觉写得挺麻烦的。说说存在的问题

1.假设a目录中既有文件又有文件夹,程序第一次执行只操作了文件,第二次操作才轮到文件夹。这个问题怎么解决好?

2.该程序并没有递归判断b目录中是否也存在相同文件,而是第二层目录后的目录直接剪切到了b目录对应位置,若是存在我用了重命名这个方式来解决,但若是后续有这个需求,程序还需要完善

3.shutil.move()在文件没其他程序占用的时候照样会被剪走,这个我感觉很不好的地方,尝试过用os.rename()。也是没有报错,这个问题有没有更好的解决方式?

  • 3
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

啊 这

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值