将Pascal-cased setter转换为下划线分隔的变量名

时间:2022-07-07 16:22:47

This is not as simple as it seems. Most of you are likely thinking of the regex /([A-Z])/_$1/ like I have found all over the Internet, but my particular situation is slightly more complicated. My source string contains more content that I don't want to have converted before a portion that I do.

这并不像看起来那么简单。大多数人可能会想到正则表达式/([A-Z])/ _ $ 1 /就像我在互联网上找到的那样,但我的特殊情况稍微复杂一些。我的源字符串包含更多内容,我不想在我做的部分之前转换。

Consider a regular setter:

考虑一个常规的二传手:

public function setUserId()

Of course, this method is missing a parameter. Perhaps I have many of these methods. I'd like to convert that line into

当然,这种方法缺少一个参数。也许我有很多这样的方法。我想把那条线转换成

public function setUserId($user_id)

which is a rather simple thing to consider, but not so simple as I ponder it deeper. It's similar to what Andreas_D in this thread, but with the added challenge of trying to iteratively modify the variable name...

这是一个相当简单的事情要考虑,但并不像我想的那么简单。它与此线程中的Andreas_D相似,但增加了尝试迭代修改变量名称的挑战......

It's probably going to be something obvious using regular expressions, but I'm still pretty new with them. Either way, I can't find a decent solution to this problem anywhere in my searches.

使用正则表达式可能会显而易见,但我对它们仍然很新。无论哪种方式,我在搜索中的任何地方都找不到合适的解决方案。

Edit: of course, I realize that there are no capitals in "public function" which leave it safe. But, this search & substitution will be running against blocks of code, and I want to ensure that the string I'm modified begins with "public function".

编辑:当然,我意识到“公共职能”中没有资本可以保证安全。但是,这个搜索和替换将针对代码块运行,我想确保我修改的字符串以“public function”开头。

1 个解决方案

#1


First search for function definitions, and then on each match, insert a parameter based on the function name.

首先搜索函数定义,然后在每次匹配时,根据函数名称插入参数。

/\b(function\s+set([A-Z]\w*))\b\s*\(\)/g

This pattern will give you matches with the function-keyword and the function name in group 1, and the camel-cased part of the function name in group 2.

此模式将为您提供与第1组中的function-keyword和函数名称匹配,以及第2组中函数名称的驼峰部分。

/([a-z](?=[A-Z])|[A-Z](?=[A-Z][a-z]))/g

This pattern will find the last letter before an upper-case/lower-case sequence that make up camel-case.

此模式将在构成驼峰大小写的大写/小写序列之前找到最后一个字母。

You didn't specify what language you will be using, so here is a demonstration using Python:

您没有指定要使用的语言,因此这是使用Python的演示:

import re

pattern1 = re.compile(r'\b(function\s+set([A-Z]\w*))\b\s*\(\s*\)')
pattern2 = re.compile(r'([a-z](?=[A-Z])|[A-Z](?=[A-Z][a-z]))')

def fix_setters(code):
    def replacer(match):
        var_name = pattern2.sub(r'\1_', match.group(2)).lower()
        return "%s($%s)" % (match.group(1), var_name)
    return pattern1.sub(replacer, code)

The last line ("return pattern1.sub(replacer, code)"), uses a callback to generate the text to be substituted. There should be similar functionality in most languages.

最后一行(“return pattern1.sub(replacer,code)”)使用回调来生成要替换的文本。在大多数语言中应该有类似的功能。

Python (before version 3.0) uses the modulus operator ("%") for formatting, similar to sprintf in e.g. the language C.

Python(版本3.0之前)使用模数运算符(“%”)进行格式化,类似于例如sprintf。语言C.

Example:

>>> s = """\
... public function setUserName() {
...   blaha
... }
... """
>>> print s
public function setUserName() {
  blaha
}

>>> print fix_setters(s)
public function setUserName($user_name) {
  blaha
}

>>>

More information: .NET - How can you split a “caps” delimited string into an array?

更多信息:.NET - 如何将“大写”分隔的字符串拆分为数组?

#1


First search for function definitions, and then on each match, insert a parameter based on the function name.

首先搜索函数定义,然后在每次匹配时,根据函数名称插入参数。

/\b(function\s+set([A-Z]\w*))\b\s*\(\)/g

This pattern will give you matches with the function-keyword and the function name in group 1, and the camel-cased part of the function name in group 2.

此模式将为您提供与第1组中的function-keyword和函数名称匹配,以及第2组中函数名称的驼峰部分。

/([a-z](?=[A-Z])|[A-Z](?=[A-Z][a-z]))/g

This pattern will find the last letter before an upper-case/lower-case sequence that make up camel-case.

此模式将在构成驼峰大小写的大写/小写序列之前找到最后一个字母。

You didn't specify what language you will be using, so here is a demonstration using Python:

您没有指定要使用的语言,因此这是使用Python的演示:

import re

pattern1 = re.compile(r'\b(function\s+set([A-Z]\w*))\b\s*\(\s*\)')
pattern2 = re.compile(r'([a-z](?=[A-Z])|[A-Z](?=[A-Z][a-z]))')

def fix_setters(code):
    def replacer(match):
        var_name = pattern2.sub(r'\1_', match.group(2)).lower()
        return "%s($%s)" % (match.group(1), var_name)
    return pattern1.sub(replacer, code)

The last line ("return pattern1.sub(replacer, code)"), uses a callback to generate the text to be substituted. There should be similar functionality in most languages.

最后一行(“return pattern1.sub(replacer,code)”)使用回调来生成要替换的文本。在大多数语言中应该有类似的功能。

Python (before version 3.0) uses the modulus operator ("%") for formatting, similar to sprintf in e.g. the language C.

Python(版本3.0之前)使用模数运算符(“%”)进行格式化,类似于例如sprintf。语言C.

Example:

>>> s = """\
... public function setUserName() {
...   blaha
... }
... """
>>> print s
public function setUserName() {
  blaha
}

>>> print fix_setters(s)
public function setUserName($user_name) {
  blaha
}

>>>

More information: .NET - How can you split a “caps” delimited string into an array?

更多信息:.NET - 如何将“大写”分隔的字符串拆分为数组?