用于重命名文件的脚本

时间:2012-01-11 15:17:12

标签: windows scripting file-rename

我在几个不同的文件夹中有大约2200个不同的文件,我需要重命名它们在自己的子文件夹中的大约1/3。那些700也在各种文件夹中。

例如,可能有 最顶层的文件夹是Employees,其中有几个文件,然后文件夹2002有几个,2003有更多的文件,2004等。

我只需在每个文件的现有名称前加上“协议”一词。因此,而不仅仅是“Joe Schmoe.doc”,而不是“协议Joe Schmoe.doc”。

我尝试使用谷歌搜索这些脚本,我可以找到类似于我想要的东西,但它看起来对我来说都很陌生,所以我无法理解我是如何修改它以满足我的需要。

哦,这是针对Windows服务器'03。

2 个答案:

答案 0 :(得分:4)

我需要大约2分钟为* NIX系统编写这样的脚本(可能更少),但对于Windows来说这是一首很长的歌...)

我为WSH编写简单的VBS脚本,尝试它(保存到{script-name} .vbs,更改Path值(在脚本的第一行)并执行)。我建议第一次在少量数据上测试脚本,以确保它是否正常工作。

Path = "C:\Users\rootDirectory"
Set FSO = CreateObject("Scripting.FileSystemObject")

Sub visitFolder(folderVar)
    For Each fileToRename In folderVar.Files
        fileToRename.Name = "Agreement " & fileToRename.Name
    Next
    For Each folderToVisit In folderVar.SubFolders
        visitFolder(folderToVisit)
    Next
End Sub

If FSO.FolderExists(Path) Then
    visitFolder(FSO.getFolder(Path))
End If

答案 1 :(得分:1)

我曾经在Windows下使用批处理脚本进行批量重命名。我知道它在* nix上很容易(找到。-maxdepth N-type f -name“$ pattern”| sed -e'p'-e“s / $ str1 / $ str2 / g”| xargs -n2 mv)。 Buf经过一番挣扎后,我发现,使用批处理脚本实现这种效果几乎是不可能的。所以我转向了javascript。

使用此脚本,您可以通过'rename.js s / ^ / Agreement /“-r * .doc'为文件名添加前缀。插入符号(^)表示匹配开头。 '-r'选项意味着'递归',即包括子文件夹。您可以使用'-d N'选项指定最大深度。如果既未给出'-r'或'-d N',则脚本不会递归。

如果您知道* nix'find'实用程序,您会注意到'find'将匹配指定正则表达式的完整路径(不仅仅是文件名部分)。可以通过提供'-f'选项来实现此行为。默认情况下,此脚本将使用给定的正则表达式匹配文件名部分。

如果您熟悉正则表达式,则可以进行复杂的重命名。例如,'rename.js's /(\ d +)/ [$ 1] /“*'使用分组将括号添加到文件名中的数字序列。

// rename.js --- bulk file renaming utility (like *nix rename.pl)
// (c) Copyright 2012, Ji Han (hanji <at> outlook <dot> com)
// you are free to distribute it under the BSD license.

// oops... jscript doesn't have array.map
Array.prototype.map = function(f, t){
    var o = Object(this);
    var a = new Array(o.length >>> 0);
    for (var i = 0; i < a.length; ++i){ if (i in o) a[i] = f.call(t, o[i], i, o) }
    return a;
};

/// main
(function(){

if (WScript.Arguments.Length == 0){
    WScript.Echo('rename "<operator>/<pattern>/<string>/[<modifiers>]" [-f] [-r] [-d <maxdepth>] [<files>]');
    WScript.Quit(1);
}

var fso = new ActiveXObject('Scripting.FileSystemObject');

// folder is a Folder object [e.g. from fso.GetFolder()]
// fn is a function which operates on File/Folder object
var recurseFolder = function(folder, fn, depth, maxdepth){
    if (folder.Files){
        for (var e = new Enumerator(folder.Files); !e.atEnd(); e.moveNext()){
            fn(e.item())
        }
    }
    if (folder.Subfolders){
        for (var e = new Enumerator(folder.SubFolders); !e.atEnd(); e.moveNext()){
            fn(e.item());
            if (depth < maxdepth){ arguments.callee(e.item(), fn, depth + 1, maxdepth) }
        }
    }
}

// expand wildcards (asterisk [*] and question mark [?]) recursively
// given path may be relative, and may contain environment variables.
// but wildcards only work for the filename part of a path.
// return an array of full paths of matched files.
// {{{
var expandWildcardsRecursively = function(n, md){
    var pattern = fso.GetFileName(n);
    // escape regex metacharacters (except  \, /, * and ?)
    // \ and / wouldn't appear in filename
    // * and ? are treated as wildcards
    pattern = pattern.replace(/([\[\](){}^$.+|-])/g, '\\$1');
    pattern = pattern.replace(/\*/g, '.*');  // * matches zero or more characters
    pattern = pattern.replace(/\?/g, '.');  // ? matches one character
    pattern = pattern.replace(/^(.*)$/, '\^$1\$');  // matches the whole filename
    var re = new RegExp(pattern, 'i');  // case insensitive
    var folder = fso.GetFolder(fso.GetParentFolderName(fso.GetAbsolutePathName(n)));
    var l = [];
    recurseFolder(folder, function(i){ if (i.Name.match(re)) l.push(i.Path) }, 0, md);
    return l;
}
// }}}

// parse "<operator>/<pattern>/<string>/[<modifiers>]"
// return an array splitted at unescaped forward slashes
// {{{
var parseExpr = function(s){
    // javascript regex doesn't have lookbehind...
    // reverse the string and lookahead to parse unescaped forward slashes.
    var z = s.split('').reverse().join('');

    // match unescaped forward slashes and get their positions.
    var re = /\/(\\\\)*(?!\\)/g;
    var l = [];
    while (m = re.exec(z)){ l.push(m.index) }

    // split s at unescaped forward slashes.
    var b = [0].concat(l.map(function(x){ return s.length - x }).reverse());
    var e = (l.map(function(x){ return s.length - x - 1 }).reverse()).concat([s.length]);
    return b.map(function(_, i){ return s.substring(b[i], e[i]) });
}
// }}}

var expr = WScript.Arguments(0);
var args = [];
var options = {};

for (var i = 1; i < WScript.Arguments.Length; ++i){
    if (WScript.Arguments(i).substring(0, 1) != '-'){
        args.push(WScript.Arguments(i));
    } else if (WScript.Arguments(i) == '-f'){
        options['fullpath'] = true;
    } else if (WScript.Arguments(i) == '-r'){
        options['recursive'] = true;
    } else if (WScript.Arguments(i) == '-d'){
        options['maxdepth'] = WScript.Arguments(++i);
    } else if (WScript.Arguments(i) == '--'){
        continue;
    } else {
        WScript.Echo('invalid option \'' + WScript.Arguments(i) +'\'');
        WScript.Quit(1);
    }
}

if (options['maxdepth']){
    var md = options['maxdepth'];
} else if (options['recursive']){
    var md = 1<<31>>>0;
} else {
    var md = 0;
}

var tokens = parseExpr(expr);
if (tokens.length != 4){
    WScript.Echo('error parsing expression \'' + expr + '\'.');
    WScript.Quit(1);
}
if (tokens[0] != 's'){
    WScript.Echo('<operator> must be s.');
    WScript.Quit(1);
}

var pattern = tokens[1];
var substr = tokens[2];
var modifiers = tokens[3];
var re = new RegExp(pattern, modifiers);

for (var i = 0; i < args.length; ++i){
    var l = expandWildcardsRecursively(args[i], md);
    for (var j = 0; j < l.length; ++j){
        var original = l[j];
        if (options['fullpath']){
            var nouveau = original.replace(re, substr);
        } else {
            var nouveau = fso.GetParentFolderName(original) + '\\' + fso.GetFileName(original).replace(re, substr);
        }
        if (nouveau != original){
            (fso.FileExists(original) && fso.GetFile(original) || fso.GetFolder(original)).Move(nouveau)
        }
    }
}

})();