Call a function on a captured group when using replace-regexp in Emacs
I learned today how to call a function on a captured group to modify the replacement text when using `replace-regexp` or `query-replace-regexp` in Emacs. A function is called by writing something like `\,(function-to-be-called \1)` in the replacement string.
Here is an example: I had to write a new Java class with a lot of getters and setters with special logic. The getters and setters had to delegate their job to special methods:
private static final String FOO_BAR = PREFIX + "FOO_BAR";
public SomeType getFooBar() {
return getValue(FOO_BAR);
}
public void setFooBar(SomeType fooBar) {
setValue(FOO_BAR, fooBar);
}
`PREFIX` is just another String constant used by the other constants.
The methods `getValue` and `setValue` are used by all generated getters and setters in that class.
I found a nice way to solve that problem using the `replace-regexp` function of Emacs. First I wrote a list of the properties, I wanted to generate, in a new buffer. The properties were written in snake case. Here is a short example:
foo_bar hello_hello
I copied the content into another buffer to generate the constants and the methods separately. I called `replace-regexp` in the first buffer to replace
\(.+\)
with
private static final String \,(upcase \1) = PREFIX + "\,(upcase \1)";
Then I switched to the second buffer and called `replace-regexp` to replace
\(.+\)
with
public SomeType get\,(s-upper-camel-case \1)() {
return getValue(\,(upcase \1));
}
public void set\,(s-upper-camel-case \1)(SomeType \,(s-lower-camel-case \1)) {
setValue(\,(upcase \1), \,(s-lower-camel-case \1));
}
After that I copied the content of each buffer into my Java class.
It is important to keep the words in the source list (e. g. "foo_bar") in lower case so `s-upper-camel-case` and `s-lower-camel-case` work as expected.