First of all, it is never a good idea to try to parse XML or other such structured text with regular expressions. While theoretically possible to do well and safely, it is extremely hard even for experts. Far better to use a dedicated tool that is designed to handle the language you have. So if this is an XML file, you could use something like xmlstarlet
instead. For example, given this input file:
$ cat file.xml
<?xml version="1.0"?>
<record id="1">
<exciton lambda="1" fix="hole"/>
</record>
You could do:
$ value="1234"
$ xml ed -u "//record[@id=1]/exciton/@lambda" -v "$value" file.xml
<?xml version="1.0"?>
<record id="1">
<exciton lambda="1234" fix="hole"/>
</record>
All that said, with the very minimal information you have given us, it is possible that you can do it using a simple, naive parser like sed
. There are various tricks you can try. First, just escape the double quotes:
$ sed "s/lambda=\"1\"/lambda=\"$value\"/" file.xml
<?xml version="1.0"?>
<record id="1">
<exciton lambda="1234" fix="hole"/>
</record>
Or, use single quotes but end them and insert the quoted variable outside the single quotes. Then, open a new single quotes sting to continue the sed
expression:
$ sed 's/lambda="1"/lambda="'"$value"'"/' file.xml
<?xml version="1.0"?>
<record id="1">
<exciton lambda="1234" fix="hole"/>
</record>
That one is a bit hard to parse visually, but this is what it is doing with added whitespace for legibility (note that it doesn't actually work with the added whitespace, this is only for clarity):
sed 's/lambda="1"/lambda="' "$value" '"/' file.xml
You have two options. First, you can simply escape the double