我正在尝试在&DEST=
和下一个&
或换行符之间获取子字符串。
例如:
MYREQUESTISTO8764GETTHIS&DEST=SFO&ORIG=6546
在此我需要提取“SFO”
MYREQUESTISTO8764GETTHIS&DEST=SANFRANSISCO&ORIG=6546
在此,我需要提取“SANFRANSISCO”
MYREQUESTISTO8764GETTHISWITH&DEST=SANJOSE
在此我需要提取“SANJOSE”
我正在逐行读取文件,我需要在&DEST=
之后更新文本并将其放回文件中。修改文本是用X字符掩盖dest值。
因此,SFO应替换为XXX。 应将SANJOSE替换为XXXXXXX。
输出:
MYREQUESTISTO8764GETTHIS&DEST=XXX&ORIG=6546
MYREQUESTISTO8764GETTHIS&DEST=XXXXXXXXXXXX&ORIG=6546
MYREQUESTISTO8764GETTHISWITH&DEST=XXXXXXX
请让我知道如何在脚本中实现这一点(最好是shell或bash脚本)。
感谢。
答案 0 :(得分:2)
$ cat file
MYREQUESTISTO8764GETTHIS&DEST=SFO&ORIG=6546
MYREQUESTISTO8764GETTHIS&DEST=PORTORICA
MYREQUESTISTO8764GETTHIS&DEST=SANFRANSISCO&ORIG=6546
MYREQUESTISTO8764GETTHISWITH&DEST=SANJOSE
$ sed -E 's/^.*&DEST=([^&]*)[&]*.*$/\1/' file
SFO
PORTORICA
SANFRANSISCO
SANJOSE
应该这样做
答案 1 :(得分:1)
让我们考虑一下这个测试文件:
$ cat file
MYREQUESTISTO8764GETTHIS&DEST=SFO&ORIG=6546
MYREQUESTISTO8764GETTHIS&DEST=SANFRANSISCO&ORIG=6546
MYREQUESTISTO8764GETTHISWITH&DEST=SANJOSE
使用等长&DEST=
并使用GNU sed替换X
之后的字符串:
$ sed -E ':a; s/(&DEST=X*)[^X&]/\1X/; ta' file
MYREQUESTISTO8764GETTHIS&DEST=XXX&ORIG=6546
MYREQUESTISTO8764GETTHIS&DEST=XXXXXXXXXXXX&ORIG=6546
MYREQUESTISTO8764GETTHISWITH&DEST=XXXXXXX
要就地替换文件:
sed -i -E ':a; s/(&DEST=X*)[^X&]/\1X/; ta' file
以上用GNU sed测试。对于BSD(OSX)sed,请尝试:
sed -Ee :a -e 's/(&DEST=X*)[^X&]/\1X/' -e ta file
或者,要使用BSD(OSX)sed进行就地更改,请尝试:
sed -i '' -Ee :a -e 's/(&DEST=X*)[^X&]/\1X/' -e ta file
如果有一些原因,为什么使用shell逐行读取文件很重要:
while IFS= read -r line
do
echo "$line" | sed -Ee :a -e 's/(&DEST=X*)[^X&]/\1X/' -e ta
done <file
让我们考虑一下这段代码:
search_str="&DEST="
newfile=chart.txt
sed -E ':a; s/('"$search_str"'X*)[^X&]/\1X/; ta' "$newfile"
-E
这告诉sed使用扩展正则表达式(ERE)。这样做的好处是需要更少的反斜杠来逃避事情。
:a
这会创建一个标签a
。
s/('"$search_str"'X*)[^X&]/\1X/
这会查找$search_str
,后跟任意数量的X
,后跟任何不是X
或&
的字符。由于parens,除了最后一个字符之外的所有内容都保存到组1中。此字符串由组1替换,表示为\1
和X
。
ta
在sed中,t
是test
命令。如果进行了替换(意味着某些字符需要被X
替换),那么测试评估为true,在这种情况下,ta
告诉sed跳转到标签a
此测试和跳转导致替换被重复多次。
$ name='DEST|ORIG'; sed -E ':a; s/(&('"$name"')=X*)[^X&]/\1X/; ta' file
MYREQUESTISTO8764GETTHIS&DEST=XXX&ORIG=XXXX
MYREQUESTISTO8764GETTHIS&DEST=XXXXXXXXXXXX&ORIG=XXXX
MYREQUESTISTO8764GETTHISWITH&DEST=XXXXXXX
$ s='MYREQUESTISTO8764GETTHIS&DEST=SFO&ORIG=6546'
$ s=${s#*&DEST=}
$ echo ${s%%&*}
SFO
工作原理:
${s#*&DEST=}
前缀删除。这将删除所有文本,包括第一次出现&DEST=
。
${s%%&*}
是后缀remove_。它会删除第一个&
到字符串末尾的所有文本。
$ echo 'MYREQUESTISTO8764GETTHIS&DEST=SFO&ORIG=6546' | awk -F'[=\n]' '$1=="DEST"{print $2}' RS='&'
SFO
工作原理:
-F'[=\n]'
这告诉awk将等号或换行视为字段分隔符
$1=="DEST"{print $2}
如果第一个字段是DEST,则打印第二个字段。
RS='&'
这会将记录分隔符设置为&
。
答案 2 :(得分:1)
使用GNU bash:
while IFS= read -r line; do
[[ $line =~ (.*&DEST=)(.*)((&.*|$)) ]] && echo "${BASH_REMATCH[1]}fooooo${BASH_REMATCH[3]}"
done < file
输出:
MYREQUESTISTO8764GETTHIS&DEST=fooooo&ORIG=6546 MYREQUESTISTO8764GETTHIS&DEST=fooooo&ORIG=6546 MYREQUESTISTO8764GETTHISWITH&DEST=fooooo
答案 3 :(得分:-1)
用x代替from c in _db.Customers
from p in _db.Payments.Where(r => r.CustId == c.ID && r.Success).OrderBy(r => r.PaymentDate).Take(1).DefaultIfEmpty()
join u1 in _db.Users on c.UserID equals u1.Id into us
from use1 in us.DefaultIfEmpty()
&& (byCard == "1" ? p!=null : true)
和&DEST
(或EOL)之间的字符:
&