Test Data:
<img src=\"images/docs/mydash_grooms.png\" alt=\"\" />
Sed:
sed 's/<img\ssrc=\\"images\/docs\/\([[:graph:]]\)/<a class=\\"popup-image\\" href=\\"images\/docs\/\1\\"><img src=\\"images\/docs\/tn.\1/g' test.txt
Output from Sed:
<a class=\"popup-image\" href=\"images/docs/m\"><img src=\"images/docs/tn.mydash_grooms.png\" alt=\"\" />
Why is my backreference not working properly both times used?
Trying to accomplish:
Changing:
<img src=\"images/docs/mydash_grooms.png\" alt=\"\" />
to
<a class=\"popup-image\" href=\"images/docs/mydash_grooms.png\"><img src=\"images/docs/tn.mydash_grooms.png\" alt=\"\" />
You have to escape the \ so they become actually "\\". However, you also have to escape the /, which makes the string very complex. I suggest replacing the delimiter of sed (i.e., the '/'), to another character to avoid complex strings. For example, using #
sed 's#<img src=\\"images/docs/\(.*\)\\" alt=\\"\\" />#<a class=\\"popup-image\\" href=\\"images/docs/\1\\"><img src=\\"images/docs/tn.\1\\" alt=\\"\\" />#g' test.txt
Futhermore, please replace the [[:graph:]], it was not working for me.
This might work for you (GNU sed):
sed -r 'h;s|img src(.*) alt.*|a class=\\"popup-image\\" href\1>|;G;s/\n//;s|(.*/)([^>])|\1tn.\2|' file
Save the line in the hold space then alter the line to replicate the first attribute. Append the original line and insert the tn. into the file name.
Related
i have text between html tags. For example:
<td>vip</td>
I will have any text between tags <td></td>
How can i cut any text from these tags and put any text between these tags.
I need to do it via bash/shell.
How can i do this ?
First of all, i tried to get this text, but without success
sed -n "/<td>/,/<\/td>/p" test.txt. But in a result i have
<td>vip</td>. but according to documentation, i should get only vip
You can try this:
sed -i -e 's/\(<td>\).*\(<\/td>\)/<td>TEXT_TO_REPLACE_BY<\/td>/g' test.txt
Note that it will only work for the <td> tags. It will replace everything between tags <td> (actually with them together and put the tags back) with TEXT_TO_REPLACE_BY.
You can use this to get the value vip
sed -e 's,.*<td>\([^<]*\)</td>.*,\1,g'
If you Input_file is same as shown example then following may help you too.
echo "<td>vip</td>" | awk -F"[><]" '{print $3}'
Simply printing the tag with echo then using awk to create a field separator >< then printing the 3rd field then which is your request.
d=$'<td>vip</td>\n<table>vip</table>\n<td>more data here</td>'
echo "$d"
<td>vip</td>
<table>vip</table>
<td>more data here</td>
awk '/<td>/{match($0,/(<.*>)(.*)(<\/.*>)/,t);print t[1] "something" t[3];next}1' <<<"$d"
<td>something</td>
<table>vip</table>
<td>something</td>
awk '/<table>/{match($0,/(<.*>)(.*)(<\/.*>)/,t);print t[1] "something" t[3];next}1' <<<"$d"
<td>vip</td>
<table>something</table>
<td>more data here</td>
The variables are
espejo=u456789
usuario=u123456
grupo=unixgr
I want to add after the line occurrence of variable $espejo, the text in variables $usuario and $grupo:
cp $DIRECTORY/usu.txt $DIRECTORY/usu.txt.`date '+%F'`
sed "/${espejo}/a\ ${usuario} ${grupo}" $DIRECTORY/usu.txt.`date '+%F'` > $DIRECTORY/usu.txt
I got this error during the execution:
sed: 0602-404 Function /u456789/a\u123456 unixgr cannot be parsed.
I don't know what is wrong.
Try the following:
sed "/${espejo}/a\
${usuario} ${grupo}" $DIRECTORIO/usu.txt.`date '+%F'` > $DIRECTORIO/usu.txt
Note that after the backslash on first line there is no any other symbols except new line.
Try this:
sed "s:${espejo}:${espejo}\n${usuario} ${grupo}:" $DIRECTORIO/usu.txt.`date '+%F'` > $DIRECTORIO/usu.txt
If the above just adds n instead of newline, try this:
sed "s:${espejo}:${espejo}\
${usuario} ${grupo}:" $DIRECTORIO/usu.txt.`date '+%F'` > $DIRECTORIO/usu.txt
This will append the new variable in new line. I guess you are facing the problem since ${espejo} contains / character in it.
This might work for you (GNU sed):
sed "/$espejo/r /dev/stdin" file <<<" ${usuario} ${grupo}"
Good Evening,
I'm trying to replace a trailing minus sign with a leading minus sign. The link below was very helpful, but I'm having a hard time dealing with both a comma and period. For example:
Input Data:
|76534| 253,453.86-| 6/4/2012| 56487-56987|
|32567| 36,000.00| 7/8/2012| 45684-4541|
|58531| 400.56-| 10/5/2012| 15232-1254|
|12584| 5.56-| 12/12/2013| 125565-451|
Desired Results (all other columns remain the same):
-253,453.86
36,000.00
-400.56
-5.56
Using sed -r 's/([[:digit:]]+(\,[[:digit:]]+(\.[[:digit:]]+)?))-/-\1/' I've been able to treat numbers with a comma, but I would like to treat all types in one command if possible.
Helpful Link:
Replace a trailing minus with leading minus
This seems to work with your multi-column data:
sed -r '{s#([0-9][0-9,.]*)-\|#-\1\|#g}'
Use [[:digit:],.] to create a character class with numbers, commas and periods. The rest you already know how to do.
sed -r 's/([[:digit:].,])-/-\1/'
You can do:
$ sed '/-$/{s/-$//;s/[0-9]/-&/;b};s/^/ /' file
-253,453.86
36,000.00
-400.56
-5.56
Updated Answer:
$ awk 'BEGIN{FS=OFS="|"}{for(i=1;i<=NF;i++)if($i~/-$/){sub(/-$/,"",$i);sub(/[0-9]/,"-&",$i)}}1' file
|76534| -253,453.86| 6/4/2012| 56487-56987|
|32567| 36,000.00| 7/8/2012| 45684-4541|
|58531| -400.56| 10/5/2012| 15232-1254|
|12584| -5.56| 12/12/2013| 125565-451|
$ awk 'BEGIN{FS=OFS="|"} sub(/-$/,"",$3){sub(/[^ ]/,"-&",$3)}1' file
|76534| -253,453.86| 6/4/2012| 56487-56987|
|32567| 36,000.00| 7/8/2012| 45684-4541|
|58531| -400.56| 10/5/2012| 15232-1254|
|12584| -5.56| 12/12/2013| 125565-451|
Another one through GNU sed,
$ sed -r 's/^(\|[0-9]+\|)( *?)([^|]*?)(-)(.*)$/\1\2\4\3\5/g' file
|76534| -253,453.86| 6/4/2012| 56487-56987|
|32567| 36,000.00| 7/8/2012| 45684-4541|
|58531| -400.56| 10/5/2012| 15232-1254|
|12584| -5.56| 12/12/2013| 125565-451|
A simple solution:
sed 's/\([^ ]*\)\-|/-\1|/' input
I have some html text that I need to fix the URL text on. I need to:
1) convert text within the URL to lowercase
also
2) converting any spaces to hyphens within the URL
also
3) deleting any parenthesis from URL
I have multiple occurances of this pattern within each file:
<div class="classname"><img src="${asset.image/url}" alt="TEXT" class="another-class-name" ></div>
Example:
I want to change this pattern: <div class="classname"><img src="${asset.image/url}" alt="TEXT" class="another-class-name" ></div>
To: <div class="classname"><img src="${asset.image/url}" alt="TEXT" class="another-class-name" ></div>
I have a number of files, and want to do an infile substitution. The /URL-EXAMPLE-ONE could have any combination of SPACE, Parenthesis too.
I now have, using the suggestion below:
/sw/bin/sed -e '/<div class="mk-man-logo-mod5-m"><a href="\/[A-Z -{}&]*"></ {
h;
s/.*<div class="mk-man-logo-mod5-m"><a href="\/\(.*\)"><img.*/\1/;
s/\(.*\)/\L\1/;
s/[ &]/-/g;
s/[()]//g;
s/<img.*//;
x;
s/\(.*<div class="mk-man-logo-mod5-m"><a href="\/\)\(.*\)\(<img.*\)/\1\3/;
G;
s/\n//;
}' $e
But the output I'm getting is, as an example:
Original text:
<div class="classname"><img src="${asset.images/common/manufacturer_logos/medium/abb-m.gif}" alt="TEXT" class="another-classname" ></div>
Transformed text:
<div class="classname"><a href="/<img src="${asset.images/url}" alt="TEXT" class="another-classname" abc-d-ediv>
Actually want:
<div class="classname"><img src="${asset.images/url}" alt="TEXT" class="another-classname"></div>
Could anyone help further?
Many thanks in advance,
Alex
A sed script to perform all of the substitutions:
sed '/<div class="classname"><a href="\/.*">/ { h; s/<div class="classname"><a href="\///; s/\(.*\)/\L\1/; s/ /-/g; s/[()]//g; x; s/\(<div class="classname"><a href="\/\)\(.*\)/\1/; G; s/\n//}'
Explanation:
/<div class="classname"><a href="\/.*">/ perform commands only if pattern matched.
h store copy of line in hold space.
s/<div class="classname"><a href="\/// remove all but the url.
s/\(.*\)/\L\1/ convert url to lower case.
s/ /-/g convert spaces to hyphens.
s[()]//g remove parentheses.
x swap hold space with pattern space (now operating on original line again)
s/\(<div class="classname"><a href="\/\)\(.*)/\1/ remove url.
G append hold space to pattern space
s/\n// remove newline introduced by G command.
Alternatively
If your data are always exactly as given in the example (ie. <div class="classname"><a href="/URL">) and you don't need a universal solution, you could use the following simpler script:
sed '/<div class="classname"><a href="\/.*">/ { s/\(.*\)/\L\1/; s/ /-/3g; s/[()]//g }'
This will match the pattern, convert everything to lowercase, delete all parentheses, and replace spaces with hyphens from the third space to the end of the line.
Update
In response to the updated question, here is a new sed command that takes into account the additional <img> tag on the end.
sed '/<div class="classname"><a href="\/[A-Z -(){}&]*"><img.*<\/div>/ { # match pattern
h; # hold copy of original string
# replace original string with just url, converted to lowercase.
s/\(<div class="classname"><a href="\/\)\([A-Z -(){}&]*\)\("><img.*<\/div>\)/\L\2/;
s/[ &]/-/g; # convert spaces, ampersands to hypens.
s/[(){}]//g; # remove parentheses, braces.
G; # append original string after url. Looks like: "converted-url\n<div class="classname"..."
s/\n//; # remove newline introduced by append G.
# swap out URL in original string with converted url.
s/\([a-z-]*\)\(<div class="classname"><a href="\/\)\([A-Z -(){}&]*\)\("><img.*<\/div>\)/\2\1\4/;
}'
Love it or hate it, sometimes Perl is the easiest.
perl -pe 's/<div class="classname"><a href="([^"]*)"/$1 =~ tr:A-Z ():a-z-:rd/e'
The regular expression could be adjusted if it is too general; I didn't do it because the regex in the OP seems to exclude hrefs with parentheses, but the request asks for parentheses to be deleted.
This may be a bit complex, but here it goes:
Assuming I have an XML that looks as follows:
<a>
<b>000</b>
<c>111</c>
<b>222</b>
<d>333</d>
<c>444</c>
</a>
How can I, using sed on a mac, get a resulting an XML that looks as follows:
<a>
<b>111 000</b>
<b>222</b>
<d>333</d>
<c>444</c>
</a>
Basically:
Matching 2 consecutive lines that are of the form <b>...</b> followed by </c>...</c>
Taking the value between <c>...</c> and placing it (plus a space character) right after <b> on the line before it
Removing the second line <c>...</c>
Thank you.
If sed is too much for this, please advise anything else as long as I can run it from a mac shell.
Not the most beautiful solution but it seams to work :-)
$ tr '\n' # < input | sed 's#<b>\([0-9]\+\)</b>#<c>\([0-9]\+\)</c>#<b>\2 \1</b#g' | tr # '\n'
output:
<a>
<b>111 000</b
<b>222</b>
<d>333</d>
<c>444</c>
</a>
or a bit more general:
$ tr '\n' # < f1 | sed 's#<b>\([^<]*\)</b>#<c>\([^<]*\)</c>#<b>\2 \1</b#' | tr # '\n'
using [^<] to match anything between brackets
Ruby would support multi-line patterns:
ruby -e 'print gets(nil).sub(/<b>([^\n]*)<\/b>\n<c>([^\n]*)<\/c>/m,"<b>\\2 \\1</b>")' file.txt