如何移动文件?

问题:如何移动文件?

我查看了Python os界面,但无法找到移动文件的方法。我将如何$ mv ...在Python中做相当于?

>>> source_files = '/PATH/TO/FOLDER/*'
>>> destination_folder = 'PATH/TO/FOLDER'
>>> # equivalent of $ mv source_files destination_folder

I looked into the Python os interface, but was unable to locate a method to move a file. How would I do the equivalent of $ mv ... in Python?

>>> source_files = '/PATH/TO/FOLDER/*'
>>> destination_folder = 'PATH/TO/FOLDER'
>>> # equivalent of $ mv source_files destination_folder

回答 0

os.rename()shutil.move()os.replace()

全部采用相同的语法:

import os
import shutil

os.rename("path/to/current/file.foo", "path/to/new/destination/for/file.foo")
shutil.move("path/to/current/file.foo", "path/to/new/destination/for/file.foo")
os.replace("path/to/current/file.foo", "path/to/new/destination/for/file.foo")

请注意,您必须file.foo在源参数和目标参数中都包含文件名()。如果更改,文件将被重命名和移动。

还请注意,在前两种情况下,用于创建新文件的目录必须已经存在。在Windows上,必须不存在具有该名称的文件,否则将引发异常,但os.replace()即使在这种情况下,它也将以静默方式替换文件。

正如在对其他答案的评论中所指出的那样,在大多数情况下,shutil.move只需调用即可os.rename。但是,如果目标与源位于不同的磁盘上,它将代替复制然后删除源文件。

os.rename(), shutil.move(), or os.replace()

All employ the same syntax:

import os
import shutil

os.rename("path/to/current/file.foo", "path/to/new/destination/for/file.foo")
shutil.move("path/to/current/file.foo", "path/to/new/destination/for/file.foo")
os.replace("path/to/current/file.foo", "path/to/new/destination/for/file.foo")

Note that you must include the file name (file.foo) in both the source and destination arguments. If it is changed, the file will be renamed as well as moved.

Note also that in the first two cases the directory in which the new file is being created must already exist. On Windows, a file with that name must not exist or an exception will be raised, but os.replace() will silently replace a file even in that occurrence.

As has been noted in comments on other answers, shutil.move simply calls os.rename in most cases. However, if the destination is on a different disk than the source, it will instead copy and then delete the source file.


回答 1

尽管os.rename()并且shutil.move()都将重命名文件,但是最接近Unix mv命令的命令是shutil.move()。区别在于,os.rename()如果源和目标位于不同的磁盘上,则shutil.move()不起作用,而与文件所在的磁盘无关。

Although os.rename() and shutil.move() will both rename files, the command that is closest to the Unix mv command is shutil.move(). The difference is that os.rename() doesn’t work if the source and destination are on different disks, while shutil.move() doesn’t care what disk the files are on.


回答 2

对于os.rename或shutil.move,您将需要导入模块。要移动所有文件,无需*字符。

我们在/ opt / awesome处有一个名为source的文件夹,其中有一个名为awesome.txt的文件。

in /opt/awesome
  ls
source
  ls source
awesome.txt

python 
>>> source = '/opt/awesome/source'
>>> destination = '/opt/awesome/destination'
>>> import os
>>> os.rename(source, destination)
>>> os.listdir('/opt/awesome')
['destination']

我们使用os.listdir来查看文件夹名称实际上已更改。这是将目标移回源的途径。

>>> import shutil
>>> shutil.move(destination, source)
>>> os.listdir('/opt/awesome/source')
['awesome.txt']

这次,我在源文件夹中进行了检查,以确保我创建的awesome.txt文件存在。在那儿:)

现在,我们已经将文件夹及其文件从源移动到了目的地,然后又移回了。

For either the os.rename or shutil.move you will need to import the module. No * character is necessary to get all the files moved.

We have a folder at /opt/awesome called source with one file named awesome.txt.

in /opt/awesome
○ → ls
source
○ → ls source
awesome.txt

python 
>>> source = '/opt/awesome/source'
>>> destination = '/opt/awesome/destination'
>>> import os
>>> os.rename(source, destination)
>>> os.listdir('/opt/awesome')
['destination']

We used os.listdir to see that the folder name in fact changed. Here’s the shutil moving the destination back to source.

>>> import shutil
>>> shutil.move(destination, source)
>>> os.listdir('/opt/awesome/source')
['awesome.txt']

This time I checked inside the source folder to be sure the awesome.txt file I created exists. It is there :)

Now we have moved a folder and its files from a source to a destination and back again.


回答 3

在Python 3.4之后,您还可以使用pathlib的类Path移动文件。

from pathlib import Path

Path("path/to/current/file.foo").rename("path/to/new/destination/for/file.foo")

https://docs.python.org/3.4/library/pathlib.html#pathlib.Path.rename

After Python 3.4, you can also use pathlib‘s class Path to move file.

from pathlib import Path

Path("path/to/current/file.foo").rename("path/to/new/destination/for/file.foo")

https://docs.python.org/3.4/library/pathlib.html#pathlib.Path.rename


回答 4

这是我目前正在使用的:

import os, shutil
path = "/volume1/Users/Transfer/"
moveto = "/volume1/Users/Drive_Transfer/"
files = os.listdir(path)
files.sort()
for f in files:
    src = path+f
    dst = moveto+f
    shutil.move(src,dst)

现在功能齐全。希望这对您有所帮助。

编辑:

我已经将其转换为一个函数,该函数接受源目录和目标目录,并创建目标文件夹(如果不存在)并移动文件。还允许过滤src文件,例如,如果您只想移动图像,则使用pattern '*.jpg',默认情况下,它将移动目录中的所有内容

import os, shutil, pathlib, fnmatch

def move_dir(src: str, dst: str, pattern: str = '*'):
    if not os.path.isdir(dst):
        pathlib.Path(dst).mkdir(parents=True, exist_ok=True)
    for f in fnmatch.filter(os.listdir(src), pattern):
        shutil.move(os.path.join(src, f), os.path.join(dst, f))

This is what I’m using at the moment:

import os, shutil
path = "/volume1/Users/Transfer/"
moveto = "/volume1/Users/Drive_Transfer/"
files = os.listdir(path)
files.sort()
for f in files:
    src = path+f
    dst = moveto+f
    shutil.move(src,dst)

Now fully functional. Hope this helps you.

Edit:

I’ve turned this into a function, that accepts a source and destination directory, making the destination folder if it doesn’t exist, and moves the files. Also allows for filtering of the src files, for example if you only want to move images, then you use the pattern '*.jpg', by default, it moves everything in the directory

import os, shutil, pathlib, fnmatch

def move_dir(src: str, dst: str, pattern: str = '*'):
    if not os.path.isdir(dst):
        pathlib.Path(dst).mkdir(parents=True, exist_ok=True)
    for f in fnmatch.filter(os.listdir(src), pattern):
        shutil.move(os.path.join(src, f), os.path.join(dst, f))

回答 5

可接受的答案不是正确的答案,因为问题不在于将文件重命名为文件,而是将许多文件移动到目录中。shutil.move会完成这项工作,但是为此目的os.rename是没有用的(如注释中所述),因为目标必须具有明确的文件名。

The accepted answer is not the right one, because the question is not about renaming a file into a file, but moving many files into a directory. shutil.move will do the work, but for this purpose os.rename is useless (as stated on comments) because destination must have an explicit file name.


回答 6

根据此处描述的答案,使用subprocess是另一种选择。

像这样:

subprocess.call("mv %s %s" % (source_files, destination_folder), shell=True)

与相比,我很想知道这种方法的优缺点shutil。因为就我而言,我已经subprocess出于其他原因使用了它,并且似乎可以使用,所以我倾向于坚持使用它。

可能取决于系统吗?

Based on the answer described here, using subprocess is another option.

Something like this:

subprocess.call("mv %s %s" % (source_files, destination_folder), shell=True)

I am curious to know the pro’s and con’s of this method compared to shutil. Since in my case I am already using subprocess for other reasons and it seems to work I am inclined to stick with it.

Is it system dependent maybe?


回答 7

这是解决方案,无法shell使用mv

import subprocess

source      = 'pathToCurrent/file.foo'
destination = 'pathToNew/file.foo'

p = subprocess.Popen(['mv', source, destination], stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
res = p.communicate()[0].decode('utf-8').strip()

if p.returncode:
    print 'ERROR: ' + res

This is solution, which does not enables shell using mv.

import subprocess

source      = 'pathToCurrent/file.foo'
destination = 'pathToNew/file.foo'

p = subprocess.Popen(['mv', source, destination], stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
res = p.communicate()[0].decode('utf-8').strip()

if p.returncode:
    print 'ERROR: ' + res

回答 8

  import os,shutil

  current_path = "" ## source path

  new_path = "" ## destination path

  os.chdir(current_path)

  for files in os.listdir():

        os.rename(files, new_path+'{}'.format(f))
        shutil.move(files, new_path+'{}'.format(f)) ## to move files from 

不同的磁盘 C:-> D:

  import os,shutil

  current_path = "" ## source path

  new_path = "" ## destination path

  os.chdir(current_path)

  for files in os.listdir():

        os.rename(files, new_path+'{}'.format(f))
        shutil.move(files, new_path+'{}'.format(f)) ## to move files from 

different disk ex. C: –> D: