my @res_word = qw( ABOUT ACCUM AND BT BTG BTI BTP FUZZY HASPATH INPATH MINUS NEAR NOT NT NTG NTI NTP OR PT RT SQE SYN TR TRSYN TT WITHIN ); my @res_char = qw( , & ? { } \ ( ) [ ] - ; ~ | $ ! > * % _ ); my $rw = join '|', @res_word; $rw = qr/$rw/; my $rc = join '', map{"\\$_"}@res_char; $rc = qr/[$rc]/; sub escape { my $str = shift; $str =~ s/($rc)/\\$1/g; # reserved char escapes $str =~ s/($rw)/{$1}/g; # reserved word escapes $str =~ s/(['"])/$1$1/g; # quote escapes return $str; }