I'm unable to use @replace[] with a % character in string2

Jul 21, 2014
9
0
France
Hi,

I need to replace the blank characters into a string with the '%20' substring.
For example: "foo bar" --> "foo%20bar"

Code:
E:\>set var=foo bar

E:\>echo %var
foo bar

E:\>echo %@replace[ ,%20,%var]
foobar

What? Oh yes, '%' is a special character, I need to escape it:

Code:
E:\>echo %@replace[ ,^%20,%var]
foo

??? I don't understand anymore. Why has the second word vanished? What did TCC understand?

Yet ^% works well outside the @replace function:
Code:
E:\>echo ^%20
%20
So how should I do to obtain "foo%20bar"?
 
Apr 18, 2014
336
9
You need to use two percent signs, both escaped...
Code:
d:\>echo %@replace[ ,^%^%20,%var]
foo%20bar
 

Charles Dye

Super Moderator
Staff member
May 20, 2008
4,689
106
Albuquerque, NM
prospero.unm.edu
Here's one way:
Code:
echo %@replace[ ,`%20`,%var]

Percent signs are always going to cause headaches for you. If you want to do anything further with the returned string, you may need to double the percent sign inside the strong quotes. Or play games with SETDOS /X.
 

samintz

Scott Mintz
May 20, 2008
1,557
26
Solon, OH, USA
This also works, but Rex will need to explain why the percents need to be quadrupled.
Code:
echo %@replace[ ,%%%%20,foo bar]
 

samintz

Scott Mintz
May 20, 2008
1,557
26
Solon, OH, USA
I sort of understand that it is creating foo%20bar and replacing %20bar with nothing because that env var is undefined. You can see this by:
Code:
set 20bar=hello
echo %@replace[ ,%%20,foo bar]
foohello
 
Jul 21, 2014
9
0
France
Thanks all for your answers, they work well.

Scott, your explanation is lucid and probably right. But the behavior of TCC differs depending on the function :
Code:
E:\>echo %@insert[2,^%20,abcd]
ab%20cd
With @insert[], one ^% is enough. But with @replace[], I have to use two ^%:
Code:
E:\>echo %@replace[ab,^%20,abcd]
ECHO est OFF

E:\>echo %@replace[ab,^%^%20,abcd]
%20cd

By the way, Charles, what is the meaning of back quotes (in `%20%`)? I found nothing about them in the help file.
I first thought that they were used to escape a whole string, but it's not so simple:
Code:
E:\>set 20bar=hello

E:\>echo %@replace[ ,`%20`,foo bar]
foo%20bar

E:\>set a=%@replace[ ,`%20`,foo bar]

E:\>echo %a
foohello
 

Charles Dye

Super Moderator
Staff member
May 20, 2008
4,689
106
Albuquerque, NM
prospero.unm.edu
By the way, Charles, what is the meaning of back quotes (in `%20%`)? I found nothing about them in the help file.
I first thought that they were used to escape a whole string, but it's not so simple:
Code:
E:\>set 20bar=hello

E:\>echo %@replace[ ,`%20`,foo bar]
foo%20bar

E:\>set a=%@replace[ ,`%20`,foo bar]

E:\>echo %a
foohello

Sorry, I missed this post. Yes, strong quotes prevent all variable expansion on whatever they enclose. So, for example:
Code:
set a=%@replace[ ,`%20`,foo bar]
will put replace any spaces in "foo bar" with the string "%20". You can verify that that is indeed what gets stored by typing:
Code:
set a

But stashing percent signs in an environment variable doesn't disarm them. They can still be used for variable expansion later on. So if you type:
Code:
echo %a
TCC wil expand replace %A with the value of environment variable A; then expand that string, replacing the %20BAR with the value of the 20BAR variable. (Or maybe with the 20th batch parameter or alias parameter, followed by "BAR".) You can use use this technique to delay variable expansion, saving expressions to be evaluated at a later time. You'll find more information under HELP QUOTING. (Rex calls these strong quotes "back quotes". I call that a "grave" misnomer, but never mind....)
 
May 20, 2008
12,175
133
Syracuse, NY, USA
The difference between these is puzzling.
Code:
v:\> echo %@insert[0,^%20,abcd]
%20abcd

v:\> echo %@replace[ab,^%20,abcd]
ECHO is OFF

v:\> echo %@replace[ab,^%^%20,abcd]
%20cd
@REPLACE's behavior is no surprise, but after the @INSERTion ("%20abcd") I'd expect ECHO to produce the value of the environment variable named "20abcd" (as Charles described).
 
May 20, 2008
12,175
133
Syracuse, NY, USA
You're not inserting "%20", you're inserting "^%20".
There's still a difference. Why doesn't @REPLACE[bc,^%20,abcd] replace "bc" with "^%20"? If it did, I'd ecpect to see the "%20" below.
Code:
v:\> echo %@replace[bc,^%20,abcd]
ECHO is OFF
With @REPLACE[] two escapes are needed.
Code:
v:\> echo %@replace[bc,^^^%20,abcd]
a%20d
 

rconn

Administrator
Staff member
May 14, 2008
12,557
167
Why would you think they would be identical? They serve different purposes.

@REPLACE does an internal "unescape" of its arguments. It has to in order to substitute special characters; @INSERT doesn't have that issue. (Note -- this is 20-year-old behavior!)
 
May 20, 2008
12,175
133
Syracuse, NY, USA
Why would you think they would be identical? They serve different purposes.

@REPLACE does an internal "unescape" of its arguments. It has to in order to substitute special characters; @INSERT doesn't have that issue. (Note -- this is 20-year-old behavior!)
What special characters? Are there characters which @INSERT can't insert because @INSERT doesn't do a similar internal "unescape"?

Yes, they have different names and they do different things. But there's something to be said for consistent behavior. On the surface (even now, to me) there doesn't seem to be a need for them to behave differently. How's the new (or old) user supposed to figure these things out?
 

rconn

Administrator
Staff member
May 14, 2008
12,557
167
There is absolutely no chance that I'm going to break a few zillion existing batch files and aliases to solve an imaginary consistency problem for you ...

You can put anything in @INSERT, but you have to unescape the line afterwards. There's no way I could do the same thing in @REPLACE, unless I disallowed all special characters in the arguments.
 

Similar threads