在Windows上与regex匹配的媒体设备上的批量重命名文件 [英] Bulk rename files on media device matched with regex on Windows

查看:71
本文介绍了在Windows上与regex匹配的媒体设备上的批量重命名文件的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我觉得我可以在使用bash的linux机器上相当容易地做到这一点,但是我对Batch的经验不足.

I feel like I could do this fairly easily on a linux machine with bash, but I don't have enough experience with Batch to do it.

基本上,我手机上的许多音乐文件都以曲目号开头:

Basically, a lot of the music files on my phone start with the track number :

01 - a song
02 - another song
03 a third song (different format)

我可以通过正则表达式匹配轻松获取所有文件:

I can easily get all of the files by a regex match:

dir /b | findstr /i "^[0-9]+ .*"

然后我假设我应该将这些值分配给一个变量.但是我可以只通过做一个for循环来做

And then I'm assuming I should assign these values to a variable. But can I do a for loop over them by just doing

for %filename in %var
     ren file [something here]

我唯一有问题的是进入媒体设备(Windows如何在幕后处理这个问题?)并删除前缀,同时处理两种可能的格式(检测'-'应该不难).我可以使用sed来做到这一点,但我不知道等效的批次.

The only thing I have issues with is getting onto the media device (how does windows handle this under the hood?) and removing the prefix, while dealing with the two possible formats (detecting the '-' shouldn't be hard). I would be able to do it with sed, but I don't know the batch equivalent.

推荐答案

无论如何我一直想这样做.

I've been meaning to do this for a while anyway.

有一个方便的 Perl重命名脚本由拉里·沃尔(Larry Wall)几年前写的,我经常使用通过regexp重命名文件.但是,由于我很少需要Windows中的Perl,并且仅为此一个脚本安装Perl似乎是一种浪费,所以我一直认为使用本机Windows脚本语言重写姓氏是个好主意.

There's a handy Perl rename script written years ago by Larry Wall that I often use to rename files via regexp. But since I rarely have need for Perl in Windows, and installing Perl just for this one script seems like a waste, I always thought it'd be a good idea to rewrite prename using native Windows scripting languages.

希望如果有任何错误,它们也不会太令人失望.我没有对脚本进行大量测试,但是对于您要重命名的文件位于当前工作目录中的基本用法而言,它似乎可以正常工作.奖励:反向引用在您的替换文字中起作用.哇!

Hopefully if there are any bugs, they won't be too debilitating. I didn't test the script a whole lot, but it seems to work fine for basic usage where the files you're renaming live in your current working directory. Bonus: backreferences work in your replacement text. Wooo.

prename.bat -v "s/searchRXP/replacement/flags" filemask

请参阅控制台窗口中的prename.bat -h以获取完整的使用帮助.

See prename.bat -h in a console window for full usage help.

<!-- : prename.bat -- http://stackoverflow.com/a/38191137/1683264
@echo off & setlocal

rem // ensure flags and other vars begin undefined
for %%I in (v n f h show filemask search replace flags) do set %%I=

rem // organize arguments
for /f "delims=" %%I in ('cscript //nologo //job:args "%~f0?.wsf" %*') do set "%%~I"
if defined h goto usage
if defined invalid (
    echo Unrecognized option: %invalid%
    goto usage
)
if not defined filemask goto usage
if not defined search goto usage
if defined v set "show=1"
if defined n set "show=1"

rem // expand wildcards
for %%I in (%filemask%) do (
    for /f "delims=" %%# in ('cscript //nologo //job:newname "%~f0?.wsf" "%%~I"') do (
        if defined show echo %%~I -^> %%~#
        if not defined n if not "%%~fI"=="%%~f#" (
            >NUL (
                if defined f (move /y "%%~I" "%%~#") else ren "%%~I" "%%~nx#"
            )
        )
    )
)

goto :EOF

:usage
echo Usage: %~nx0 [-v] [-n] [-f] perlexpr [filelist]
echo    -v shows verbose output
echo    -n performs a simulation only
echo    -f forces overwriting existing files
echo    perlexpr is a Perl-compatible regular expression
echo    filelist can contain wildcards
echo;
echo Example:
echo    %~nx0 -n "s/([^\.]+)$/\1.cmd/i" *.bat
echo This would simulate renaming every .bat file extension to .bat.cmd
goto :EOF

: end batch begin JScript hybrid code -->
<package>
    <job id="args">
        <script language="JScript">
            var args = {
                    v: 0,
                    n: 0,
                    f: 0,
                    h: 0,
                    search: '',
                    replace: '',
                    flags: '',
                    filemask: ''
                };

            for (var i=0; i<WSH.Arguments.length; i++) {
                if (/^[\/-](.)/.test(WSH.Arguments(i))) {
                    if (typeof args[RegExp.$1] === 'undefined')
                        args.invalid = WSH.Arguments(i);
                    args[RegExp.$1] = 1;
                }
                else if (/^s(\W)(.+)\1(.*)\1(.*)/.test(WSH.Arguments(i))) {
                    args.search = RegExp.$2;
                    args.replace = RegExp.$3;
                    args.flags = RegExp.$4;
                }
                else args.filemask += ';' + '"' + WSH.Arguments(i) + '"';
            }
            for (var i in args) if (args[i]) WSH.Echo(i + '=' + args[i]);
        </script>
    </job>
    <job id="newname">
        <script language="JScript">
            var env = WSH.CreateObject('WScript.Shell').Environment('Process'),
                search = env('search'),
                repl = env('replace'),
                flags = env('flags');

            WSH.Echo(WSH.Arguments(0).replace(
                new RegExp(search, flags),
                function(full, $1, $2, $3, $4, $5, $6, $7, $8, $9) {
                    var backref = [full, $1, $2, $3, $4, $5, $6, $7, $8, $9];
                    return repl.replace(
                        /[\\$](\d)/g,
                        function(full, $1) { return backref[$1]; }
                    );
                }
            ));
        </script>
    </job>
</package>

这篇关于在Windows上与regex匹配的媒体设备上的批量重命名文件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆