tags:

views:

224

answers:

5

Regular Expressions are a complete void for me. I'm dealing with one right now in TextMate that does what I want it to do...but I don't know WHY it does what I want it to do.

/[[:alpha:]]+|( )/(?1::$0)/g

This is used in a TextMate snippet and what it does is takes a Label and outputs it as an id name. So if I type "First Name" in the first spot, this outputs "FirstName". Previously it looked like this:

/[[:alpha:]]+|( )/(?1:_:/L$0)/g (it might have been \L instead)

This would turn "First Name" into "first_name". So I get that the underscore adds an underscore for a space, and that the /L lowercases everything...but I can't figure out what the rest of it does or why.

Someone care to explain it piece by piece?

EDIT

Here is the actual snippet in question:

<column header="$1"><xmod:field name="${2:${1/[[:alpha:]]+|( )/(?1::$0)/g}}"/></column>
+1  A: 

it's searching for any alpha character that appears at least once in a row [[:alpha:]]+ or space ( ).

Agent_9191
+1  A: 
/[[:alpha:]]+|( )/(?1::$0)/g

The (?1 is a conditional and used to strip the match if group 1 (a single space) was matched, or replace the match with $0 if group 1 wasn't matched. As $0 is the entire match, it gets replaced with itself in that case. This regex is the same as:

/ //g

I.e. remove all spaces.

/[[:alpha:]]+|( )/(?1:_:/\L$0)/g

This regex is still using the same condition, except now if group 1 was matched, it's replaced with an underscore, and otherwise the full match ($0) is used, modified by \L. \L changes the case of all text that comes after it, so \LABC would result in abc; think of it as a special control code.

Roger Pate
+5  A: 

This regular expression (regex) format is basically:

 /matchthis/replacewiththis/settings

The "g" setting at the end means do a global replace, rather than just restricting the regex to a particular line or selection.

Breaking it down further...

  [[:alpha:]]+|( )

That matches an alpha numeric character (held in parameter $0), or optionally a space (held in matching parameter $1).

  (?1::$0)

As Roger says, the ? indicates this part is a conditional. If a match was found in parameter $1 then it is replaced with the stuff between the colons :: - in this case nothing. If nothing is in $1 then the match is replaced with the contents of $0, i.e. any alphanumeric character that is not a space is output unchanged.

This explains why the spaces are removed in the first example, and the spaces get replaced with underscores in your second example.

In the second expression the \L is used to lowercase the text.

The extra question in the comment was how to run this expression outside of TextMate. Using vi as an example, I would break it into multiple steps:

:0,$s/ //g
:0,$s/\u/\L\0/g

The first part of the above commands tells vi to run a substitution starting on line 0 and ending at the end of the file (that's what $ means).

The rest of the expression uses the same sorts of rules as explained above, although some of the notation in vi is a bit custom - see this reference webpage.

Dan J
Will this regex syntax work outside of TextMate?I'm assuming that as I type in TextMate it is only working on the character that I just typed.How would this regex be written to apply it to an entire file?
Pselus
See updated answer above for an example outside of TextMate.
Dan J
+1  A: 

This is a pretty thorough resource for regular expressions in TextMate. Cheers.

Diakonia7
+2  A: 

I find RegexBuddy a good tool for me in dealing with regexs. I pasted your 1st regex in to Buddy and I got the explanation shown in the bottom frame:

RegexBuddy

I use it for helping to understand existing regexs, building my own, testing regexs against strings, etc. I've become better @ regexs because of it. FYI I'm running under Wine on Ubuntu.

Chris
Interesting tactic, suggesting a Windows-only program in response to a question about a Mac-only program. ;)
mipadi
lol nice, I didn't even think of that. ;) As I mentioned I was running under Ubuntu/Wine. Per http://www.regexbuddy.com/usercomm.html "it works fine in Parallels on OS-X".
Chris