Javascript 正则表达式 - 如何在组内查找 PascalCase 项

Javascript regex- How to find PascalCase items inside of group

我需要像这样转换:

[[Click here|ThisIsALink]]

至:

[Click here](https://example.com/this-is-a-link)

我可以通过使用此正则表达式 /\[\[(.*?)\|(.*?)\]\]/g 找到第一个 [[Click here|ThisIsALink]],我可以将其替换为 [Click here](https://example.com/ThisIsALink]),但是我该如何处理最后一部分并将其转换为 this-is-a-link?我已经尝试了一些事情,但我似乎找到了所有 PascalCased 事件,而不仅仅是在第一个找到的正则表达式模式中发生的事件。 (我正在将 .md 文件转换为 .pdf,所以它是一整页的内容,而不仅仅是这些链接)。

这是我目前所拥有的

var exampleUrl = "https://example.com/";
var urlOne = /\[\[(.*?)\|(.*?)\]\]/g;

data.replace(urlOne, "[](" + exampleUrl + ")"));

这导致: [Click here](https://example.com/ThisIsALink)

您可以使用

const texts = ["Text [[Click here|ThisIsALink]] text...",
               "Text [[Click here|This-Is-A-Link]] text..."];
const exampleUrl = "https://example.com/";
const urlOne = /\[\[((?:(?!\[\[).)*?)\|(.*?)]]/g;
for (var text of texts) {
  console.log(
    text.replace(urlOne, (_,x,y) =>
                 `[${x}](${exampleUrl}${y.replace(/[^A-Za-z]+/g, '')
                                         .replace(/(?!^)[A-Z]/g, '-$&')
                                         .toLowerCase()})`) );
}

正则表达式 #1 详细信息:

  • \[\[ - [[ 字符串
  • ((?:(?!\[\[).)*?) - 第 1 组:除换行符以外的任何字符,零次或多次,尽可能少,不开始 [[ 字符序列
  • \| - 一个 | 字符
  • (.*?) - 第 2 组:除换行字符外的任何零个或多个字符,尽可能少
  • ]] - ]] 字符串。

第二个正则表达式(?!^)[A-Z] 应用于第 2 组内容,并匹配任何不在字符串开头的大写 ASCII 字母。 -$& 替换只是在匹配之前附加 -

额外的正则表达式 .replace(/[^A-Za-z]+/g, '') 将在插入连字符之前从第 2 组内容中删除所有 non-alpha 个字符。

这种方法确实会在任何给定长度的文本中找到并替换 OP 提到的模式,而不管该模式在该文本中的匹配频率如何。

它还使用非常简单的正则表达式 String.prototype.replace

正则表达式看起来确实是这样的……/\[\[([^|]+)\|([^\]]+)\]\]/g……读起来是这样的……

  1. \[\[ ... 匹配(字面意思)两个左方括号 ...
  2. ([^|]+) ... 捕获每个字符序列 (link 文本) 不是管道 ...
  3. \| ...然后匹配一个管道 ...
  4. ([^\]]+) ... 捕获每个字符序列 (非常 url) 不是右方括号 ...
  5. \]\] ... 然后匹配两个右方括号。
  6. / ... /g ... 将正则表达式标记为全局 processed/applied 模式。

const sampleUrl = 'https://example.com/'
const sampleText = `Text [[Link A|ThisIsLinkA]] text. Text [[Link B|thisIsLinkB]] text.
Text [[Link C|This-Is-Link-C]] text.
Text [[Link D|ThisIsLinkD]] text. Text [[Link E|-this--Is--Link--E]] text.`;

function convertLinkMarkup(text, baseUrl) {
  function ensureKebabCase(str) {
    return str
      .replace((/([A-Z])/g), '-') // - prefix any latin uppercase char with '-'.
      .replace((/-+/g), '-')        // - replace any '-' sequence with a single '-'.
      .replace((/^-+/g), '')        // - trim any leading '-' sequence.
      .toLowerCase();               // - lower-case the result.
  }
  function createLinkMarkup(match, text, path) {
    return `[${ text }](${ baseUrl }${ ensureKebabCase(path) })`;
  }
  const regXUrl = (/\[\[([^|]+)\|([^\]]+)\]\]/g);

  return text.replace(regXUrl, createLinkMarkup);
}

console.log(
  sampleText,
  '\n\n... => ...\n\n',
  convertLinkMarkup(sampleText, sampleUrl)
);
.as-console-wrapper { min-height: 100%!important; top: 0; }