标题: [文本处理] 【已解决】gawk:如何提取指定个数范围的字符 [打印本页]
作者: 思想之翼 时间: 4 天前 02:50 标题: 【已解决】gawk:如何提取指定个数范围的字符
本帖最后由 思想之翼 于 2024-12-1 10:19 编辑
D:\JZ\A.txt 每行记录若干字符,格式如下:
G B B
B C C C A
J A
J
E
E D
【问题】如何用gawk,提取指定个数范围N的字符?
若指定N=2,结果为J A E
若指定N=3,结果为B C
若指定N=4,结果为空
若指定N=2、3,结果为J A E B C
若指定N=2、4,结果为J A E
若指定N=2、3、4,结果为J A E B C
下列代码,只能提取指定个数N=2的字符- gawk -v"N=2" -v"RS=\r?\n| " -v"ORS= " "{++d[$0]}END{for(i in d)if(d[i]==N)print i}" "D:\JZ\A.txt">"D:\JZ\B.txt"
复制代码
作者: Five66 时间: 4 天前 05:18
不知行否 ,任意非数字分割 ,输出无序- gawk -v"N=2,3、4" -v"RS=\r?\n| " -v"ORS= " "{++d[$0]}END{split(N,M,/[^0-9]+/);for(j in M){for(i in d)if(d[i]==M[j])print i}}" "D:\JZ\A.txt">"D:\JZ\B.txt"
复制代码
作者: 思想之翼 时间: 4 天前 10:47
回复 2# Five66
感谢帮助!结果正确。若N=50-100,共有51个数值,如何简洁表达?
作者: hfxiang 时间: 4 天前 11:04
回复 3# 思想之翼 - gawk -v"N=50-100" -v"RS=\r?\n| " -v"ORS= " "{++d[$0]}END{split(N,M,/-/);for(j=M[1];j<=M[2];j++){for(i in d)if(d[i]==j)print i}}" "D:\JZ\A.txt">"D:\JZ\B.txt"
复制代码
作者: 思想之翼 时间: 4 天前 11:25
本帖最后由 思想之翼 于 2024-12-1 11:26 编辑
回复 4# hfxiang
感谢帮助!结果正确。再请教细节问题:若N=50-70,74,78,94-96,98,100,如何简洁设置?
作者: hfxiang 时间: 4 天前 13:11
本帖最后由 hfxiang 于 2024-12-1 13:48 编辑
回复 5# 思想之翼 - gawk -v"N=40,50-70,74,78,94-96,98,100" -v"RS=\r?\n| " -v"ORS= " "{++d[$0]}END{split(N,M,/[^0-9]+/,s);A[M[1]];for(j in s){if(s[j]==\"-\"){for(i=M[j];i<=M[j+1];i++)A[i]}else{A[M[j+1]]}};for(j in A){for(i in d)if(d[i]==j)print i}}" "D:\JZ\A.txt">"D:\JZ\B.txt"
复制代码
作者: 思想之翼 时间: 4 天前 16:56
本帖最后由 思想之翼 于 2024-12-1 17:03 编辑
回复 2# Five66
感谢!结果正确。
作者: 思想之翼 时间: 4 天前 17:14
回复 6# hfxiang
感谢!结果正确。加入下列变量,运行出错,是正则表达式[^0-9]的原因吗?如何处置?- @echo off
- setlocal enabledelayedexpansion
- for /l %%d in (1,1,2) do (
- set o=%%d
- gawk -v"N=40,50-70,74,78,94-96,98,100" -v"RS=\r?\n| " -v"ORS= " "{++d[$0]}END{split(N,M,/[^0-9]+/,s);A[M[1]];for(j in s){if(s[j]==\"-\"){for(i=M[j];i<=M[j+1];i++)A[i]}else{A[M[j+1]]}};for(j in A){for(i in d)if(d[i]==j)print i}}" "D:\JZ1\!o!.txt">"D:\JZ2\!o!.txt"
- )
- endlocal
- exit
复制代码
作者: hfxiang 时间: 4 天前 17:23
回复 8# 思想之翼
经套用脚本测试,/[^0-9]+/没问题,你能确定如下文件确实存在?
"D:\JZ1\!o!.txt" "D:\JZ2\!o!.txt"
作者: 思想之翼 时间: 4 天前 18:02
本帖最后由 思想之翼 于 2024-12-1 18:03 编辑
回复 9# hfxiang
感谢关注!不知道问题出在哪?
运行下列代码,结果正确:- gawk -v"N=2,4,13,40,50-70,74,78,94-96,98,100" -v"RS=\r?\n| " -v"ORS= " "{++d[$0]}END{split(N,M,/[^0-9]+/,s);A[M[1]];for(j in s){if(s[j]==\"-\"){for(i=M[j];i<=M[j+1];i++)A[i]}else{A[M[j+1]]}};for(j in A){for(i in d)if(d[i]==j)print i}}" D:\JZ1\1.txt > D:\JZ2\1.txt]
复制代码
运行下列代码,不输出文本:- @echo off
- setlocal enabledelayedexpansion
- for /l %%d in (1,1,2) do (
- set o=%%d
- gawk -v"N=2,4,13,40,50-70,74,78,94-96,98,100" -v"RS=\r?\n| " -v"ORS= " "{++d[$0]}END{split(N,M,/[^0-9]+/,s);A[M[1]];for(j in s){if(s[j]==\"-\"){for(i=M[j];i<=M[j+1];i++)A[i]}else{A[M[j+1]]}};for(j in A){for(i in d)if(d[i]==j)print i}}" D:\JZ1\!o!.txt > D:\JZ2\!o!.txt
- )
- endlocal
- exit
复制代码
测试文本 1.txt 2.txt 记录数值相同,格式如下:
G B B
B C C C
J A A A A
J
E
E D
0000 0000 0000 0000 0000
0000 0000 0000 0000 0000
0000 0000 0000
作者: hfxiang 时间: 4 天前 19:25
回复 10# 思想之翼
建立"D:\JZ1\1.txt"及"D:\JZ1\2.txt"文件,创建"D:\JZ2"文件夹后,用以下脚本调用gawk 4.1.0 ( http://bcn.bathome.net/tool/4.1.0/gawk.exe )测试完全正常- @echo off
- for /l %%d in (1,1,2) do (
- gawk -v"N=2,4,13,40,50-70,74,78,94-96,98,100" -v"RS=\r?\n| " -v"ORS= " "{++d[$0]}END{split(N,M,/[^0-9]+/,s);A[M[1]];for(j in s){if(s[j]==\"-\"){for(i=M[j];i<=M[j+1];i++)A[i]}else{A[M[j+1]]}};for(j in A){for(i in d)if(d[i]==j)print i}}" "D:\JZ1\%%~d.txt" > "D:\JZ2\%%~d.txt"
- )
复制代码
作者: 77七 时间: 4 天前 19:46
回复 8# 思想之翼
开启延迟变量扩展,多了次预处理,改为 [^^0-9]
作者: Five66 时间: 4 天前 20:26
本帖最后由 Five66 于 2024-12-1 20:45 编辑
回复 3# 思想之翼
非范围数字任意非 - 符号分割(注意特殊字符) ,范围数字 - 符号分割- gawk -v"N=2,4,13 40#50-70,74-,78,94-96/98,,100" -v"RS=\r?\n| " -v"ORS= " "{++d[$0]}END{split(N,L,/[0-9]+-[0-9]+|[0-9]+/,W);for(i in W){if(split(W[i],Z,/-/)>1){for(j=Z[1];j<=Z[2];j++)M[j]}else{M[W[i]]}};for(j in M){for(i in d)if(d[i]==j)print i}}" "D:\JZ\A.txt">"D:\JZ\B.txt"
复制代码
作者: WHY 时间: 4 天前 22:59
- @echo off
- setlocal enabledelayedexpansion
- for %%i in (1-3,5-15,20) do (
- set "s=%%i"
- if "!s:-=!" NEQ "!s!" (
- for /L %%j in (!s:-^= 1 !) do set "n=!n! %%j"
- ) else (
- set "n=!n! %%i"
- )
- )
- gawk -v"RS=\\s+" -v"ORS= " "{++d[$0]};END{split(\"!n:~1!\",a);for(i in d)for(j in a)if(d[i]==a[j])print i}" 1.txt > 2.txt
- pause
复制代码
欢迎光临 批处理之家 (http://www.bathome.net/) |
Powered by Discuz! 7.2 |