正则表达式分割驼峰式字符串

95

我在JavaScript中有一个正则表达式,用以下代码(此代码来自这里)来将我的驼峰字符串按大写字母拆分:

"MyCamelCaseString"
    .replace(/([A-Z])/g, ' $1')
    .replace(/^./, function(str){ return str.toUpperCase(); })

因此返回:

"My Camel Case String"

这很不错。但是,我想再进一步。有人能帮我写一个正则表达式吗?只有在前一个字符为小写字母且后一个字符为大写字母时才进行分割。

因此,上述示例将得到我期望的结果,但如果我输入:

"ExampleID"

然后我得到返回:

"Example ID"

不是

"Example I D"

因为它会在每个大写字母处进行分割,忽略之前的任何内容。

希望这样说起来有意义!谢谢 :)


http://www.regular-expressions.info/lookaround.html - Mchl
9
(高级) -- 甜。 - devnull
我的驼峰字符串 - urzeit
1
可能是RegEx to split camelCase or TitleCase (advanced)的重复问题。 - Samuel Liew
3
尝试使用 replace(/([a-z])([A-Z])/g, '$1 $2')。 (将小写字母和大写字母之间的空格替换为一个空格) - urzeit
我从标题中删除了“(高级)”一词,以防人们不知道@devnull在说什么。它并不真正属于那里。 - Joe
15个回答

0

最近我遇到了这个问题,需要做同样的事情:

employeeID 应该被渲染为 员工编号

我发现这个 大小写转换库 来自 zellwk 再加上一点额外的 reduce 函数就可以解决我的问题:

import { toTitle } from "./convert-case.js";

// NB. Assumes sequential single chars can be concatenated
// ex. N B A Finals => NBA Finals
const reducer = (total, currentValue, currentIndex, arr) => {
  if (
    currentValue.length === 1 &&
    !(currentIndex > 0 && arr[currentIndex - 1].length > 1)
  ) {
    return total + currentValue;
  } else {
    return total + " " + currentValue;
  }
};

const concatSingleChars = (title) => {
  const arrTitle = title.split(" ");
  return arrTitle.reduce(reducer);
};

const convertCase = (str) => {
  const s = toTitle(str);
  return concatSingleChars(s);
};

const tests = [
  "colName",
  "This_Is_A_title",
  "And_How_About_thisOne",
  "MaryHadALittleLamb",
  "employeeID",
  "N B A Finals",
  "N B A Finals in L A",
  "I Love L A"
];

const titles = tests.map((test) => {
  return convertCase(test);
});

console.log(titles);

0

我更喜欢使用数组而不是字符串。这样更容易调试和更灵活。这是一个实际的join而不是replace。我还没有处理字符串中的空格,但你可以很容易地修剪每个元素。

const splitCamelCase = str => str.match(/^[A-Z]?[^A-Z]*|[A-Z][^A-Z]*/g).join(' ');

console.log(splitCamelCase('fooMyCamelCaseString'));
console.log(splitCamelCase('MyCamelCaseString'));
console.log(splitCamelCase('XYZMyCamelCaseString'));
console.log(splitCamelCase('alllowercase'));


1
但是 'ExampleID'.match(/^[A-Z]?[^A-Z]*|[A-Z][^A-Z]*/g).join(' ') 给了我 Example I D。我希望它能给我 Example ID - kimbaudi

0

这是我从Github Copilot得到的内容 - 解释是我的,这不是完全由AI生成的:

  1. 通过/([A-Z])/g正则表达式在大写字母前加一个空格。
  2. 通过/^./正则表达式将字符串开头的任何内容大写。
  3. 使用.trim()方法修剪前导和尾随空格。

这是最终代码:

function camelCaseToCapitalized(str: string) {
  return str
    .replace(/([A-Z])/g, " $1")
    .replace(/^./, (str) => str.toUpperCase())
    .trim();
}

0

你可以使用正则表达式(regEx)、替换(replace)和修剪(trim)的组合。

"ABCMyCamelCaseSTR".replace(/([A-Z][a-z0-9]+)/g, ' $1 ')
                   .replace(/\s{2}/g," ").trim()

// ABC My Camel Case STR

由于您在正则表达式中添加了 0-9,因此最好提供一个包含数字字符的示例字符串(例如:"ABCMy22Camel123CaseSTR" 返回 "ABC My22 Camel123 Case STR")。 - kimbaudi
1
此外,你的解决方案无法处理 lowerCamelCase 字符串。"ExampleID".replace(/([A-Z][a-z0-9]+)/g, ' $1 ').replace(/\s{2}/g," ").trim() 返回 Example ID,但 exampleID 仍会返回 exampleID 而不是 example ID - kimbaudi

-4

这个正则表达式字符串是

.replace("/([a-zA-Z][a-z]*)/g",...);

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接