1748233 Members
3332 Online
108759 Solutions
New Discussion юеВ

problems with "/"

 
SOLVED
Go to solution
Pando
Regular Advisor

problems with "/"

Dear Gurus,

Am trying to replace certain line in my file

For Example:

Product Name,XXX/YY

What i want to do is replace XXX/YY with the following:

Product Name,XXX/YY-Dir

and i have the following line in my script:

export ddev=$(awk -F "," '/^Product Name/ {print $2}' $FILE|awk -F " " '{print $1}')
perl -pi -e "s/^Product Name,$ddev/Product Name,$ddev"-"$Dir/" $FILE

the ddev variable sometime contains "/" that it does not contain the correct match because of the "/" and causes an error.

I know something is wrong in the perl command.

Please help!
8 REPLIES 8
Dennis Handly
Acclaimed Contributor

Re: problems with "/"

>the ddev variable sometime contains "/" that it does not contain the correct match because of the "/" and causes an error.

It seems ddev is set by awk and that will have the "/". It seems you must tell perl that you must use a different delimiter other than the "/"?

(Any reason you are using both awk and perl instead of just one tool?)

Hein van den Heuvel
Honored Contributor

Re: problems with "/"

For you immediate question, just use something other then "/" as the delimitors in the substitute command. For example use ";".

perl -pi -e "s;^Product Name,$ddev;Product Name,$ddev"-"$Dir;" $FILE

But why jump through that double AWK hoop?
Perl can do it all!

It looks like you simply want

(untested)

perl -pi -e 's/(^ProductName.*)$/$1-Dir/' $FILE

That is... if a line starts with product name then remember everything up to the EOL in $1 and replace it by $1-dir.

You could also have done that in AWK:

awk '/^ProductName/{$0 = $0 "-Dir"} {print}' $FILE

Oh wait... $Dir is a variable also.
Where does it come from? Pick up also?
Or pass it as a parameter or variable.

awk -v dir=$Dir '/^ProductName/{$0 = $0 "-" dir} {print}' $FILE


Enjoy,
Hein.








Sandman!
Honored Contributor

Re: problems with "/"

Choose a different delimiter within the substitution command.

Instead of:
"s/pattern_to_match/replacement_pattern/p"
use:
"s%pattern_to_match%replacement_pattern%p"

Replace the "/" with "%" or with any character that is unambiguous, one that is not found in the pattern you're trying to match. The two lines in your script can be replaced by a single one for compacting code and improving its legibility.

replace...
export ddev=$(awk -F "," '/^Product Name/ {print $2}' $FILE|awk -F " " '{print $1}')
perl -pi -e "s/^Product Name,$ddev/Product Name,$ddev"-"$Dir/" $FILE

...with
# sed -n "/^Product Name/s%\(.*\)%&-$Dir%p" $FILE

hope it helps!
Pando
Regular Advisor

Re: problems with "/"

Hello Hein and Sandman,

Thanks for your reply.
I have tested both solutions and the results are the same. The output i got was:

Product Name,XXX/YY -

The output i needed to continue my is script should be:

Product Name,XXX/YY-Dir

Where Dir is a Variable also.

Am attaching my script and a file for you to check. Thanks!
Dennis Handly
Acclaimed Contributor
Solution

Re: problems with "/"

Your problem is that you are trying to pass the shell variable $Dir to perl. You can't do that easily if you have to use single quotes. It is better to pass an extra parm to your perl script.

But if you insist, you can use massive quoting:
perl -pi -e "s/(^Product Name.*)$/\$1-$Dir/"

(I had to quote the "$1".)

To do something similar with awk, you use -v to set the variable.
Sandman!
Honored Contributor

Re: problems with "/"

You're not getting the expected output because (already stated in Dennis' post) of single quotes which prevent variable expansion. Moreover using "/" within the substitution command will prevent parsing of the line owing to ambiguity if $Dir contains slashes "/".

For example...

Dir=/home/mydir

and the input file contains:
Product Name,XXX/YY

sed -n '/^Product Name/s/.*/&-$Dir/p' $FILE
Product Name,XXX/YY-$Dir

notice that variable $Dir has not been expanded to its contents "/home/mydir". Now replace single quotes with double quotes and try the command again:

sed -n "/^Product Name/s/.*/&-$Dir/p" $FILE
sed: Function /^Product Name/s/.*/&-/home/mydir/p cannot be parsed.

the command errors out owing to the presence of "/" characters in $Dir variable, so change the substitution command delimiters to an unambiguous character such as "|" or ";" etc.

sed -n "/^Product Name/s|.*|&-$Dir|p" $FILE
Product Name,XXX/YY-/home/mydir

which gives the expected output.

~hope it helps
Hein van den Heuvel
Honored Contributor

Re: problems with "/"

Pando,

The relevant answers have already been given.
Some free advice though!

Read up a little more on perl and get ready for a 'paradigm shift'. The shell script you show uses perl but really is a classic Unix shell which just happens to use perl as a tool. Might as well use awk/sed.

Perl will happily do all the tasks in a single activation, and faster!

For sure the two substitutes can simply be part of one command/program.

But also the ls + awk $9 can be readily replaced by "glob": while (<*>)
In doing so perl will have the file names in its local variables ready to play with.

Btw... why ask for an 'ls -l' and then extract just the name? Why not simply use 'ls'?
Old>> ls -l * | awk '{print $9}' |while read FILE
New?? For FILE in 'ls'


Enjoy!
Hein.

Pando
Regular Advisor

Re: problems with "/"

Thanks guys for the quick replies!
This forum is realy great!