Batch file 区分大小写的字符串操作

Batch file 区分大小写的字符串操作,batch-file,cmd,Batch File,Cmd,假设我们有一个变量,比如 set test=This is a Test string. 我们希望用大写的X替换每个小写的t,以获得所需的输出 This is a TesX sXring. 我尝试使用字符串操作set test=%test:t=X%,但它将每个t替换为X。我也尝试过@dbenham,但无法解决此问题。要将其保留在纯批处理中,您可以逐个字符进行区分大小写的比较: @ECHO OFF SETLOCAL EnableDelayedExpansion SET String=This

假设我们有一个变量,比如

set test=This is a Test string.
我们希望用大写的
X
替换每个小写的
t
,以获得所需的输出

This is a TesX sXring.

我尝试使用字符串操作
set test=%test:t=X%
,但它将每个
t
替换为
X
。我也尝试过@dbenham,但无法解决此问题。

要将其保留在纯批处理中,您可以逐个字符进行区分大小写的比较:

@ECHO OFF
SETLOCAL EnableDelayedExpansion

SET String=This is a test.
SET "Result="

REM Process each char.
FOR /L %%A IN (0,1,999) DO (
    SET Char=!String:~%%A,1!
    REM Case sensitive char replacement.
    IF "!Char!" EQU "t" SET Char=X

    REM Append result.
    SET Result=!Result!!Char!
)

REM Output will be: This is a XesX.
ECHO %Result%

ENDLOCAL

没有本机批处理命令可以方便地执行区分大小写的字符串操作。本机批处理解决方案必须在循环中逐个字符构建新的字符串。非常可行-但是很痛苦,而且效率也很低

编辑—很久以前,我编写了一个名为的纯批处理实用程序,它对文本文件的内容进行区分大小写的查找/替换。性能不错,但也有一些限制。我很少使用这种代码。我编写了一个配套例程,对变量(而不是文本文件)执行区分大小写的查找/替换,但我似乎丢失了该代码

今天,每当我想操纵文本时,我几乎总是使用

您的示例的解决方案应该是:

for /f delims^=^ eol^= %%A in ('jrepl t X /s test') do set "test=%%A"
但似乎有一个bug。如果变量名不是
test
的某个名称,则它可以工作。看起来我有一些调试要做

在修复错误之前,您可以使用:

for /f delims^=^ eol^= %%A in ('cmd /v:on /c "echo(!test!)|jrepl t X"') do set "test=%%A"


更新:该错误在3.4版中已修复。
/S
选项现在与名为
TEST
的变量一起工作。如果您不需要完整的jrepl.bat功能,您可以制作自己的混合批处理脚本来使用JScript的
String.prototype.replace()
功能

@if (@CodeSection == @Batch) @Then
@echo off
setlocal

set test=This is a Test string.

:: invoke JScript and capture result to %test%
for /f "delims=" %%I in ('cscript /nologo /e:Jscript "%~f0" "%test%"') do (
    set "test=%%I"
)

echo %test%

goto :EOF

:: end batch / begin JScript
@end

WSH.Echo(WSH.Arguments(0).replace(/t/g, 'X'));
输出:

This is a TesX sXring.
Input:  This is a Test string.
Change "t" by "X":
Output: This is a TesX sXring.

Input:  This Test String Have Two "t" Letters joined Together.
Change "t" by "X":
Output: This TesX SXring Have Two "X" LeXXers joined TogeXher.
或者,如果您不介意使用PowerShell命令,
-creplace
执行区分大小写的替换

@echo off
setlocal

set test=This is a Test string.
set psCommand=powershell -command "'%test%' -creplace 't','X'"

for /f "delims=" %%I in ('%psCommand%') do set "test=%%I"

echo %test%

相同的输出。

我不认为下面的纯批量解决方案效率低下(更换只需两条线,没有回路)。它唯一的限制是替换字符串中最多25个字母:

编辑:我修复了一个错误,它错误地替换了几个搜索字母,这些字母仅由一个替换字母连接在一起

@echo off
setlocal EnableDelayedExpansion

set find=t
set repl=X

rem Prepare the replacement auxiliary variables (just once)
set "join=%%a"
for %%a in (b c d e f g h i j k l m n o p q r s t u v w x y z) do set "join=!join!%repl%%%%%a"

rem First method: fail when two search letters are joined together
set test=This is a Test string.

echo Input:  %test%
echo Change "%find%" by "%repl%":
for /F "tokens=1-26 delims=%find%" %%a in ("%test%¡") do call set "out=%join%"
for /F "delims=¡" %%a in ("%out%") do set "out=%%a"
echo Output: %out%

echo/

rem Second method: previous bug fixed
set test=This Test String Have Two "t" Letters joined Together.

echo Input:  %test%
echo Change "%find%" by "%repl%":
for /F "tokens=1-26 delims=%find%" %%a in ("!test:%find%%find%=%find%¿%find%!¡") do call set "out=%join%"
for /F "delims=¡" %%a in ("%out%") do set "out=%%a"
set "out=!out:%repl%¿%repl%=%repl%%repl%!"
echo Output: %out%
输出:

This is a TesX sXring.
Input:  This is a Test string.
Change "t" by "X":
Output: This is a TesX sXring.

Input:  This Test String Have Two "t" Letters joined Together.
Change "t" by "X":
Output: This TesX SXring Have Two "X" LeXXers joined TogeXher.

您在
get options
批处理代码中使用了一个
test
变量来屏蔽输入变量。我可以问一下/f delims^=^eol^=的
功能是什么?为什么会有插入符号?你能解释一下吗?@MCND-是的,我一看代码就发现了问题。我已经切换到名为
/TEST
的变量,并更新了文档以指出变量名称中的限制。通常,任何不以
/
开头的内容。具体来说,不能匹配选项名称或
/TEST
@JohnDOE-FOR/F命令处理命令的输出。奥术DELIMS和EOL语法是禁用这两个选项以确保所有值都被保留的唯一方法,而不管主角是什么。您的特定示例不需要它,但通常您可能不知道前导字符是什么,并且您不希望它与EOL字符匹配。有一种简单而高效的纯批处理方法,可以将一个字母区分大小写替换为另一个字母。请参阅…即使使用第二种方法“bug fix”,仍然存在主要问题:尝试使用
set“test=t tt ttt ttt tttt”
。结果=
T XX XX XX XXT XX┐X XX┐当然,搜索和替换单个字符相对简单。但是,如果搜索和替换字符串的长度都可以变化,则情况会变得更加复杂。我以前写过这样的例行公事,但这很痛苦。您确实需要知道输入字符串和搜索字符串的长度。@dbenham-同意这不是最有效的方法,因为您总是需要逐位置进行比较,而批处理没有获取字符串长度的本机方法。我所能找到的这种方法的最佳“优化”是通过寻找一个空字符串,然后退出,从而使循环短路。因此,不要总是运行999次迭代。有关非常快速的批处理strlen函数,请参阅。另外,请查看我的文档中的modfile.bat链接。