lethargic_man: (Default)
Lethargic Man (anag.) ([personal profile] lethargic_man) wrote2007-04-02 11:24 am

You couldn't make this up...

Somewhere back in the history of MS-DOS, or probably in the pre-Micros~1 Q-DOS stage, backslash was adopted as the directory separator character. I don't know who was responsible for this, but things would have been a lot simple if the forward slash had been chosen instead, as used in Unix (and URLs), because backslashes are typically used to encode control characters, to escape things, and in regular expressions.

The reason I bring this up is because I have a Windows filename, C:\Documents and Settings\me\Local Settings\Temp\myfile.txt, which I am trying to interpolate into another string, in Java. It should be a simple case of myString.replaceFirst ("file_here", filename). But that won't work, because backslashes have a special meaning in regular expressions. So we need to escape the backslashes. And the way we do that is to use a backslash. So, we have to replace every \ in filename with \\.

The problem with this is that all three of the above backslashes need escaping, so as to ensure they are interpreted as literal backslashes and not anything else. (This wouldn't be a problem if Java had a non-interpolating string format, like Perl's single-quoted strings.) Hence what we actually have to specify is to replace \\ in filename with \\\\.

Only that still won't work, because although \\ evaluates to \, this would be interpreted as the single backslash introducing another character, to create the likes of "\n", so we need to escape this backslashes to make sure that that doesn't happen. And the way to do that is to use backslashes. And these, of course, have to be escaped.

In summary, in order to interpolate filename into myString and get exactly the same filename in the resulting string you had in your original one, you have to use myString.replaceFirst ("file_here", filename.replaceAll ("\\\\", "\\\\\\\\").

As I said, you couldn't make this up.

(Of course, I could avoid this problem by not using String.replaceAll(), but it is the simplest way, and, like Mt Everest, it's there...)

[identity profile] pseudomonas.livejournal.com 2007-04-02 11:16 am (UTC)(link)
I don't know about Java, but in perl you can use forward-slashes regardless of the OS and they'll be automagically fixed. so open SYS, 'C:/Windows/system/foo.txt' will do what you mean. I'm not sure what this does to MS filenames that *contain* forward-slashes as part of the name.
ext_8103: (Default)

[identity profile] ewx.livejournal.com 2007-04-02 11:34 am (UTC)(link)
I believe that it was in DOS 2, and that the reason was that they'd already used / as an option character (that being the convention in the CP/M world they were rooted in). It was, indeed, a horrendous decision, and has caused much more pain since than changing the option character to (for instance) the UNIX convention of '-' would have done.