排序CSV记录

时间:2019-06-13 20:48:35

标签: csv batch-file cmd

我正在尝试使用批处理脚本对特定列上的csv文件进行排序。

csv文件大约有22列,而L(10)列包含邮政编码。有多个具有相同邮政编码的记录,我需要按数字升序对这些记录进行排序。

这是我到目前为止所做的,

for /F "tokens=1-22 delims=," %%a in (test.csv) do (
   rem Define the sorting column in next line: %%a=1, %%b=2, etc...
   set "line["%%l"]=%%d,%%f,%%l"
)

for /F "tokens=1* delims==" %%a in ('set line[') do echo %%b >> result2.txt

这是我的结果。它正在删除具有重复邮政编码的记录。我应该看到具有相同邮政编码但名称不同的多行。

"John","Doe","12078" 
"John","Doe3","12095"  
"John","Doe5","12197"

或(%csv)中的%% f做(    SET CurrentFile = %% f    SET / a NumLines = 0

   For /f %%j in ('Find "" /v /c ^< !CurrentFile!') Do (
   Set /a NumLines=%%j




    (set row=%~1) & (set last=%~1)
   For /F "tokens=4-7 delims=," %%D in ('type !CurrentFile!') do (
        if not defined row (set row=%%D %%F) else (set last=%%D %%F)

    )
   echo.    
   echo. Filename: !CurrentFile! 
       echo. Record Count: !NumLines! 
       echo. First Record Name:!row! 
       echo. Last Record Name: !last! 

) >> Result.txt

) ENDLOCAL

2 个答案:

答案 0 :(得分:0)

setlocal EnableDelayedExpansion

for /F "tokens=1-22 delims=," %%a in (test.csv) do (
   rem Define the sorting column in next *three lines*: %%a=1, %%b=2, etc...
   if not defined V%%~l set "V%%~l=1000"
   set /A "V%%~l+=1"
   set "line[%%~l!V%%~l!]=%%d,%%f,%%l"
)

for /F "tokens=1* delims==" %%a in ('set line[') do echo %%b >> result2.txt

如果有多个具有相同邮政编码的记录,则有必要标识每个记录。此解决方案使用一个名为V<zip code>的变量作为具有相同邮政编码的每个记录的计数器。然后,将此类变量的 value 与邮政编码本身连接起来,以便为每个记录创建唯一的键。该程序假定最多有999条具有相同邮政编码的记录。如果此值还不够,只需在if not defined V%%~l set "V%%~l=1000"行中添加零...

答案 1 :(得分:0)

@ECHO OFF
SETLOCAL
SET "sourcedir=U:\sourcedir"
SET "destdir=U:\destdir"
SET "filename1=%sourcedir%\q56588370.txt"
SET "outfile=%destdir%\outfile.txt"
SET "sortfile=%destdir%\sortfile.txt"

SET /a sortcol=3

(
FOR /f "usebackqdelims=" %%a IN ("%filename1%") DO (
 rem full line in %%a
 SET "fullline=%%a"
 CALL :sub %%a
)
)>"%sortfile%"

(
FOR /f "tokens=1*delims=+" %%a IN (' sort "%sortfile%"') DO (
 ECHO %%b
)
)>"%outfile%"

DEL "%sortfile%"

GOTO :EOF

:sub
IF %sortcol% neq 1 FOR /L %%z IN (2,1,%sortcol%) DO SHIFT
ECHO %1+%fullline%
GOTO :eof

您需要根据自己的情况更改sourcedirdestdir的设置。

我使用了一个名为q56588370.txt的文件,其中包含一些虚拟数据用于测试。

产生定义为%outfile%的文件。 %sortfile%只是一个临时文件,具有您在合理范围内所需的名称。

检索文件的每一行,并将其内容分配给变量fullline,然后对每一行执行子例程:sub,并将整行作为参数传递。由于每行必须是用逗号分隔的项列表,可以是带引号的字符串,也可以是不包含空格或逗号的字符串,因此可以由子例程将其解码,因此所需要做的只是{{1} }参数列表(必须为-1)次,所需的排序数据在shift中。

输出%1,后跟定界符,并将最初读取的整行(对一系列语句加括号并重定向,将通常在屏幕上显示的数据发送到重定向目标)到临时文件中,对其进行排序并删除使用选定的定界符在每行前面添加数据。

通过这种方式,可以选择多个列,并根据需要操作数据-例如,本地“邮政编码”为4位数字(可以%1开头)而其他国家/地区则使用其他格式,或者可以记录和处理可能会应用于ZIP的广受欢迎的扩展代码。

这是我的测试数据:

0

并输出:

"John","Doe","12345","moredata 1"
"John","Do, or not","12345","moredata 2"
"John","Doe 4","12344","moredata 3"
"John","Doe 5","12345","moredata 4"
"John","Doe 6","12345","moredata 5"
"John","Doe 7","12344","moredata 6"