我有一个包含用户信息的CSV文件。我正在尝试创建一个简单的批处理,允许任何人输入名称或名称或公司的一部分,如果找到结果,则很好地显示它。 csv文件有四列:名称,公司,城市,州 name列有一个逗号,但已用双引号括起来。
[myfile.csv]
Name,Company,City,State
"Smith, John",ACME,Buffalo,NY
"Doe, Jane",Disney,Orlando,FL
[/ myfile.csv]
[searchcsv.bat]
@echo off
cls
setlocal enabledelayedexpansion
set CSVFILE=myfile.csv
:HOME
cls
set column=""
echo ---- USER SEARCH TOOL ----
echo ---- By: Dimitri ----
echo.
echo 1 Search By Name
echo 2 Search By Company
echo X Close
echo.
Choice /C 12X /N /M "Please make a selection: "
echo.
IF ERRORLEVEL 3 GOTO :EXIT
IF ERRORLEVEL 2 GOTO :SCHCOMP
IF ERRORLEVEL 1 GOTO :SCHNAME
:SCHNAME
set column=lname
echo ---- Enter Last Name ----
set /p strsearch=
cls
GOTO :FINDIT
:SCHCOMP
set column=Company
echo ---- Enter Company -----
set /p strsearch=
cls
GOTO :FINDIT
:FINDIT
for /f "skip=1 tokens=*" %%A in (%CSVFILE%) do (
set inline=%%A
for /f "tokens=1-5 delims=," %%1 in ("!inline!") do (
set lname=%%1&set fname=%%2&set comp=%%3&set cit=%%4&set stat=%%5
if %column% equ %strsearch% ( GOTO :SHOWRES ) ELSE ( GOTO :NFOUND )
)
)
:SHOWRES
echo Company: %comp%
echo Name: %lname%,%fname%
echo City: %cit%
echo State: %stat%
pause
GOTO :Home
:NFOUND
echo NOT FOUND Try AGAIN
pause
GOTO :HOME
[/ searchcsv.bat]
我希望我可以按姓氏,名字搜索,但由于名字中的逗号,往往会搞砸。
无论如何,希望有人可以指出我做错了什么。感谢您的帮助。
-Dimitri
答案 0 :(得分:2)
@ECHO OFF
cls
setlocal enabledelayedexpansion
set CSVFILE=myfile.csv
:HOME
cls
set column=""
echo ---- USER SEARCH TOOL ----
echo ---- By: Dimitri ----
echo.
echo 1 Search By Name
echo 2 Search By Company
echo X Close
echo.
Choice /C 12X /N /M "Please make a selection: "
echo.
IF ERRORLEVEL 3 GOTO :EOF
IF ERRORLEVEL 2 GOTO SCHCOMP
IF ERRORLEVEL 1 GOTO SCHNAME
:SCHNAME
set column=lname
echo ---- Enter Last Name ----
set /p strsearch=
GOTO FINDIT
:SCHCOMP
set column=Company
echo ---- Enter Company -----
set /p strsearch=
GOTO FINDIT
:FINDIT
CLS
SET found=N
for /f "skip=1 tokens=*" %%A in (%CSVFILE%) do (
set inline=%%A
for /f "tokens=1-5 delims=," %%a in ("!inline!") do (
set lname=%%~a&set fname=%%~b&set comp=%%~c&set cit=%%~d&set stat=%%~e
CALL SET fname=!fname:"=!
if %column% equ Company CALL :MATCH "%%~c"
if %column% equ lname CALL :MATCH "%%~a"
)
)
IF %found%==N echo NOT FOUND Try AGAIN
pause
GOTO :Home
:MATCH
SET matchto=%~1
CALL SET matchto=%%matchto:%strsearch%=%%
IF "%matchto%"==%1 GOTO :EOF
SET found=Y
:SHOWRES
echo Company: %comp%
echo Name: %lname%,%fname%
echo City: %cit%
echo State: %stat%
GOTO :eof
这是一个修订过的例程。我不会说这是防弹......
第一个问题是你不能使用数字作为你的元变量(%%x
中的for ...%%x
) - 它必须是字母的,并且区分大小写。 (好吧 - 一些符号也可以工作) - 所以 - 上面的%%a
和%%A
是不同的。
下一步:您的数据在针对进行标记时,可能会产生不平衡的引号,例如"Smith
和Jane"
。这些可能导致批次错误。通常情况下,解决方法是将变量赋值给%%~x
,其中〜删除封闭的引号 - 但只有当第一个字符为“时它才会这样做,因此要求“手动”剥离lname
上的引号。
下一篇:数据问题。你可能希望完全匹配,但是输入Cholmondley-Snodgrass
是一件痛苦的事。特别是如果你坚持一个案例匹配。此外,您的数据中可能有多少Smith
个?就此而言,有时不止一个人为公司工作。
因此,在搜索开始时设置标志found
并在找到匹配时将其设置为其他值将允许您选择是否显示失败消息。在修订的例程中CALL
MATCH
,将公司名称或姓氏作为第一个参数传递意味着您只需将strsearch
与传递的值匹配即可。它在引号中传递,以满足包含空格的di Maggio
之类的名称。
匹配例程尝试将strsearch
中的matchto
替换为 = 之后的字符串 - 这是空的。如果是matchto
,则会更改found
找到匹配的子字符串。因此,如果它保持不变,则不匹配,否则设置goto :label
标志并显示记录数据。
我个人厌恶goto :EOF
语法。当然,它有效。唯一需要的是. The problem is that there **IS** a difference - not with
,其预定义为'此批处理文件的结尾but with
转到.
来电and
来电:标签{{1}}来电标签是两件不同的事情。第一个将例程 INTERNAL 调用到此批处理文件,而第二个调用具有名称的单独批处理文件。如果只在需要时使用:,会容易得多。也可以更快地打字。
答案 1 :(得分:0)
您的代码有几个小错误:
:SCHCOMP
set column=Company
comp
下方,但存储公司的变量仅命名为set column=comp
,因此上一行必须更改为lname
。fname
和delims=,
变量的值包含引号,因为%%~1
。您必须使用%%~2
和if %column% equ %strsearch% ( GOTO :SHOWRES ) ELSE ( GOTO :NFOUND )
删除引号。if %column% equ %strsearch% ...
,如果第一个值不是搜索值,则代码会立即转到NFOUND,其余值不会被比较。您需要消除ELSE部分并重新排列代码。if /I "!%column%!" equ "%strsearch%" ...
"列"变量包含搜索变量的名称(" lname"或" comp"),但您不想比较此名称,而是值这样的变量,因此需要额外的延迟扩展:@echo off
cls
setlocal enabledelayedexpansion
set CSVFILE=myfile.csv
:HOME
cls
set column=""
echo ---- USER SEARCH TOOL ----
echo ---- By: Dimitri ----
echo.
echo 1 Search By Name
echo 2 Search By Company
echo X Close
echo.
Choice /C 12X /N /M "Please make a selection: "
echo.
IF ERRORLEVEL 3 GOTO :EXIT
IF ERRORLEVEL 2 GOTO :SCHCOMP
IF ERRORLEVEL 1 GOTO :SCHNAME
:SCHNAME
set column=lname
echo ---- Enter Last Name ----
set /p strsearch=
cls
GOTO :FINDIT
:SCHCOMP
set column=comp
echo ---- Enter Company -----
set /p strsearch=
cls
GOTO :FINDIT
:FINDIT
for /f "skip=1 tokens=*" %%A in (%CSVFILE%) do (
set inline=%%A
for /f "tokens=1-5 delims=," %%1 in ("!inline!") do (
set "lname=%%~1" & set "fname=%%~2" & set "comp=%%3" & set "cit=%%4" & set "stat=%%5"
if /I "!%column%!" equ "%strsearch%" GOTO :SHOWRES
)
)
:NFOUND
echo NOT FOUND Try AGAIN
pause
GOTO :HOME
:SHOWRES
echo Company: %comp%
echo Name: %lname%,%fname%
echo City: %cit%
echo State: %stat%
pause
GOTO :Home
:EXIT
。此外,将比较值括在引号中并使用/ I开关也很方便。虽然这不是错误,但我建议您不要在FOR命令可替换参数中使用数字。您应始终使用字母并保留批处理文件可替换参数的数字。
{{1}}