我需要使用具有相同行数的过滤器文件对文本文件进行一系列替换:过滤器的n
行应应用于原始文件的n
行。
例如原始文件:
foo
bar
foobar
过滤文件:
s/oo/uu/
s/a/i/
s/b/l/
预期结果:
fuu
bir
foolar
由于sed
将在每行上应用每个过滤器,因此使用sed -f filterfile
的效率特别低(行数相当大,因此N²
也相当大……)。此外,尽管在我的特殊情况下,我可以修改过滤器来避免此问题,但是此命令将导致示例错误的结果。
我目前正在实施以下方法(仍在尝试解决列表问题...):
paste -d'@' filterA filterB infile \
|while IFS="@" read AA BB LINE;
do
echo $LINE|"s/$AA/$BB/g"
done > outfile
但是我想知道是否有更优雅的解决方案,例如一些sed
选项? (最好使用标准的GNU / Linux工具。)
答案 0 :(得分:3)
您可以通过在每行前面添加适当的行地址来修改过滤器文件
$ nl filter
1 s/oo/uu/
2 s/a/i/
3 s/b/l/
然后将其通过管道传递到sed:
$ nl filter | sed -f- infile
fuu
bir
foolar
如果需要全局替换,请先附加g
:
$ sed 's/$/g/' filter
s/oo/uu/g
s/a/i/g
s/b/l/g
导致
sed 's/$/g/' filter | nl | sed -f- infile
替换后开始下一个循环的一个小的优化是在其后添加一个b
命令:
sed 's/.*/{&g;b}/' filter | nl | sed -f- infile
这将立即开始下一个循环。对于该问题,输入和过滤器文件的30,000行版本的效果大约可节省20%的时间:
$ wc -l filter infile
33033 filter
33033 infile
66066 total
$ time sed 's/$/g/' filter | nl | sed -f- infile >/dev/null
real 0m15.868s
user 0m15.522s
sys 0m0.296s
$ time sed 's/.*/{&g;b}/' filter | nl | sed -f- infile >/dev/null
real 0m12.238s
user 0m11.901s
sys 0m0.271s
如果文件很大,awk会快得多(代码由Ed Morton提供):
$ time awk 'NR==FNR{o[NR]=$2;n[NR]=$3;next} {gsub(o[FNR],n[FNR])} 1' filter infile >/dev/null
real 0m0.073s
user 0m0.061s
sys 0m0.007s
答案 1 :(得分:2)
(function(i, s, o, g, r, a, m) {
i['GoogleAnalyticsObject'] = r;
i[r] = i[r] || function() {
(i[r].q = i[r].q || []).push(arguments)
}, i[r].l = 1 * new Date();
a = s.createElement(o),
m = s.getElementsByTagName(o)[0];
a.async = 1;
a.src = g;
m.parentNode.insertBefore(a, m)
})(window, document, 'script', '//www.google-analytics.com/analytics.js', 'ga');
ga('create', 'UA-44871699-2', 'auto');
ga('require', 'displayfeatures');
//updated to track page query string and hash
ga('send', 'pageview', {
'page': location.pathname + location.search + location.hash
});
//Function for tracking links
function trackOutboundLinks(category, action, label, url) {
ga('send', 'event', category, action, label)
}
//Testing it with the below event
var $cart = $('#cart-checkout')
$cart.on('click', function() {
console.log('clicked');
trackOutboundLinks("cart", "click", "logo", $(this).attr("href"));
});
以上内容可在任何UNIX盒中的任何shell中使用任何awk进行工作。