我想用c#将一个目录的全部内容从一个位置复制到另一个位置。

使用System似乎没有办法做到这一点。没有大量递归的IO类。

如果我们添加对Microsoft的引用,VB中有一个方法可以使用。VisualBasic:

new Microsoft.VisualBasic.Devices.Computer().
    FileSystem.CopyDirectory( sourceFolder, outputFolder );

这似乎是一个相当丑陋的黑客。有没有更好的办法?


当前回答

下面的代码复制所有文件从源到目标给定的模式在相同的文件夹结构:

public static void Copy()
        {
            string sourceDir = @"C:\test\source\";
            string destination = @"C:\test\destination\";

            string[] textFiles = Directory.GetFiles(sourceDir, "*.txt", SearchOption.AllDirectories);

            foreach (string textFile in textFiles)
            {
                string fileName = textFile.Substring(sourceDir.Length);
                string directoryPath = Path.Combine(destination, Path.GetDirectoryName(fileName));
                if (!Directory.Exists(directoryPath))
                    Directory.CreateDirectory(directoryPath);

                File.Copy(textFile, Path.Combine(directoryPath, Path.GetFileName(textFile)), true);
            }
        }

其他回答

这个网站总是帮助我很多,现在轮到我用我所知道的帮助其他人了。

我希望我下面的代码对某些人有用。

string source_dir = @"E:\";
string destination_dir = @"C:\";

// substring is to remove destination_dir absolute path (E:\).

// Create subdirectory structure in destination    
    foreach (string dir in System.IO.Directory.GetDirectories(source_dir, "*", System.IO.SearchOption.AllDirectories))
    {
        System.IO.Directory.CreateDirectory(System.IO.Path.Combine(destination_dir, dir.Substring(source_dir.Length + 1)));
        // Example:
        //     > C:\sources (and not C:\E:\sources)
    }

    foreach (string file_name in System.IO.Directory.GetFiles(source_dir, "*", System.IO.SearchOption.AllDirectories))
    {
        System.IO.File.Copy(file_name, System.IO.Path.Combine(destination_dir, file_name.Substring(source_dir.Length + 1)));
    }

或者,如果你想走一条艰难的路,为你的微软项目添加一个引用。然后使用下面的代码:

Microsoft.VisualBasic.FileIO.FileSystem.CopyDirectory(fromDirectory, toDirectory);

然而,使用一个递归函数是一个更好的方法,因为它不需要加载VB dll。

只是想加上我的版本。它可以处理目录和文件,如果目标文件存在,则可以覆盖或跳过。

public static void Copy(
    string source,
    string destination,
    string pattern = "*",
    bool includeSubFolders = true,
    bool overwrite = true,
    bool overwriteOnlyIfSourceIsNewer = false)
{
    if (File.Exists(source))
    {
        // Source is a file, copy and leave
        CopyFile(source, destination);
        return;
    }

    if (!Directory.Exists(source))
    {
        throw new DirectoryNotFoundException($"Source directory does not exists: `{source}`");
    }

    var files = Directory.GetFiles(
        source,
        pattern,
        includeSubFolders ?
            SearchOption.AllDirectories :
            SearchOption.TopDirectoryOnly);

    foreach (var file in files)
    {
        var newFile = file.Replace(source, destination);
        CopyFile(file, newFile, overwrite, overwriteOnlyIfSourceIsNewer);
    }
}

private static void CopyFile(
    string source,
    string destination,
    bool overwrite = true,
    bool overwriteIfSourceIsNewer = false)
{
    if (!overwrite && File.Exists(destination))
    {
        return;
    }

    if (overwriteIfSourceIsNewer && File.Exists(destination))
    {
        var sourceLastModified = File.GetLastWriteTimeUtc(source);
        var destinationLastModified = File.GetLastWriteTimeUtc(destination);
        if (sourceLastModified <= destinationLastModified)
        {
            return;
        }

        CreateDirectory(destination);
        File.Copy(source, destination, overwrite);
        return;
    }

    CreateDirectory(destination);
    File.Copy(source, destination, overwrite);
}

private static void CreateDirectory(string filePath)
{
    var targetDirectory = Path.GetDirectoryName(filePath);
    if (targetDirectory != null && !Directory.Exists(targetDirectory))
    {
        Directory.CreateDirectory(targetDirectory);
    }
}

你可以一直使用这个,摘自微软网站。

static void Main()
{
    // Copy from the current directory, include subdirectories.
    DirectoryCopy(".", @".\temp", true);
}

private static void DirectoryCopy(string sourceDirName, string destDirName, bool copySubDirs)
{
    // Get the subdirectories for the specified directory.
    DirectoryInfo dir = new DirectoryInfo(sourceDirName);

    if (!dir.Exists)
    {
        throw new DirectoryNotFoundException(
            "Source directory does not exist or could not be found: "
            + sourceDirName);
    }

    DirectoryInfo[] dirs = dir.GetDirectories();
    // If the destination directory doesn't exist, create it.
    if (!Directory.Exists(destDirName))
    {
        Directory.CreateDirectory(destDirName);
    }

    // Get the files in the directory and copy them to the new location.
    FileInfo[] files = dir.GetFiles();
    foreach (FileInfo file in files)
    {
        string temppath = Path.Combine(destDirName, file.Name);
        file.CopyTo(temppath, false);
    }

    // If copying subdirectories, copy them and their contents to new location.
    if (copySubDirs)
    {
        foreach (DirectoryInfo subdir in dirs)
        {
            string temppath = Path.Combine(destDirName, subdir.Name);
            DirectoryCopy(subdir.FullName, temppath, copySubDirs);
        }
    }
}

下面的代码是微软建议如何复制目录 由亲爱的@iato分享 但是它只是递归地复制源文件夹的子目录和文件,而不复制源文件夹本身(如右键单击->复制)。

但在这个答案下面有一个棘手的方法:

private static void DirectoryCopy(string sourceDirName, string destDirName, bool copySubDirs = true)
        {
            // Get the subdirectories for the specified directory.
            DirectoryInfo dir = new DirectoryInfo(sourceDirName);

            if (!dir.Exists)
            {
                throw new DirectoryNotFoundException(
                    "Source directory does not exist or could not be found: "
                    + sourceDirName);
            }

            DirectoryInfo[] dirs = dir.GetDirectories();
            // If the destination directory doesn't exist, create it.
            if (!Directory.Exists(destDirName))
            {
                Directory.CreateDirectory(destDirName);
            }

            // Get the files in the directory and copy them to the new location.
            FileInfo[] files = dir.GetFiles();
            foreach (FileInfo file in files)
            {
                string temppath = Path.Combine(destDirName, file.Name);
                file.CopyTo(temppath, false);
            }

            // If copying subdirectories, copy them and their contents to new location.
            if (copySubDirs)
            {
                foreach (DirectoryInfo subdir in dirs)
                {
                    string temppath = Path.Combine(destDirName, subdir.Name);
                    DirectoryCopy(subdir.FullName, temppath, copySubDirs);
                }
            }
        }

如果你想递归复制源文件夹和子文件夹的内容,你可以像这样简单地使用它:

string source = @"J:\source\";
string dest= @"J:\destination\";
DirectoryCopy(source, dest);

但是如果你想复制源目录自己(类似于你右键单击源文件夹,然后单击复制,然后在目标文件夹中单击粘贴),你应该像这样使用:

 string source = @"J:\source\";
 string dest= @"J:\destination\";
 DirectoryCopy(source, Path.Combine(dest, new DirectoryInfo(source).Name));