简体   繁体   English

重击,查找和替换-重复使用变量?

[英]Bash, find and replace - re-use with variable?

I'm building a script in bash that goes and finds references to other files (such as a reference in an html file to an img source (image.jpg) 我正在bash中构建一个脚本,该脚本可以查找其他文件的引用(例如html文件中对img源的引用(image.jpg)

The problem is that I'm using sed to replace all instances that contain (in this example) "/some/random/directory/image.jpg" 问题是我正在使用sed替换包含(在此示例中) “ / some / random / directory / image.jpg”的所有实例

The "some/random/directory/image.jpg" is going to be differen every single time so when it comes to my sed line I need to use regex, but in order to find the line to replace I need to include image.jpg . “ some / random / directory / image.jpg”每次都会有所不同,因此,在我的sed行中,我需要使用正则表达式,但是要找到要替换的行,我需要包含image.jpg

so for example my sed line would be something like 因此,例如,我的s​​ed行将类似于

sed 's/\/some\/random\/directory\/image.jpg/images\/image.jpg/g'

But how do I get the end of whats in the find and put it into the replace? 但是,如何才能找到内容的结尾并将其替换? (In this example it would be image.jpg . Is there some way to make that a variable? (在此示例中为image.jpg 。是否可以通过某种方法将其设置为变量?

Here's my script as it stands now: 这是我现在的脚本:

#!/bin/bash

cd /home/username/www/immrqbe/

for file in $(grep -rlI ".jpg" *)
do
sed -e "s/\".*\/.*.jpg//ig" $file > /tmp/tempfile.tmp
mv /tmp/tempfile.tmp /home/username/www/immrqbe/$file
done

This obviously isn't functional complete as I need help with it but you get the idea of how I'd like to have it complete. 这显然不是功能完整的,因为我需要它的帮助,但是您了解了我希望如何完成它。

What you're looking for is called a Backreference in the world of regular expressions. 您正在寻找的东西在正则表达式世界中称为反向引用 You want to refer back to a previously matched string. 您想参考以前匹配的字符串。

There are a couple of ways to do this with sed, but what you want to use is the grouping mechanism: \\( and \\) . 使用sed可以使用多种方法,但是要使用的分组机制是\\(\\) Anything sed finds between \\( and \\) will be put into a group and you can refer back to that group using \\n where n is the number of the group that you want to use, from left to right. sed在\\(\\)之间找到的任何内容都将被放入一个组,您可以使用\\n返回该组,其中n是您要使用的组的编号,从左到右。

So, in your example, you want: 因此,在您的示例中,您需要:

sed 's/".*\/\(.\+\.jpg\)"/\1/ig' file

Your filename will be in the \\(.\\+\\.jpg\\) group and you can then refer to it using \\1 in the replacement section. 您的文件名将位于\\(.\\+\\.jpg\\)组中,然后可以在替换部分中使用\\1进行引用。


As a side note, notice that, as long as you don't want the shell to expand a variable in your quoted string, you can use single quotes and avoid escaping the double quotes in your pattern. 另外,请注意,只要您不希望外壳程序在带引号的字符串中扩展变量,就可以使用单引号,并避免在模式中转义双引号。

使用括号捕获匹配项,然后使用反斜杠对其进行引用。

sed -e 's/".*\/\(.*.jpg\)/\1/ig'

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM