JavaScript - การอ้างอิง regex สตริง


95

คุณสามารถอ้างอิงย้อนกลับเช่นนี้ใน JavaScript:

var str = "123 $test 123";
str = str.replace(/(\$)([a-z]+)/gi, "$2");

สิ่งนี้จะ (ค่อนข้างโง่) แทนที่ "$ test" ด้วย "test" แต่ลองนึกดูว่าฉันต้องการส่งสตริงผลลัพธ์ $ 2 ไปยังฟังก์ชันซึ่งจะคืนค่าอื่น ฉันลองทำสิ่งนี้ แต่แทนที่จะได้รับสตริง "test" ฉันได้รับ "$ 2" มีวิธีที่จะบรรลุนี้หรือไม่?

// Instead of getting "$2" passed into somefunc, I want "test"
// (i.e. the result of the regex)
str = str.replace(/(\$)([a-z]+)/gi, somefunc("$2"));

คำตอบ:


120

แบบนี้:

str.replace(regex, function(match, $1, $2, offset, original) { return someFunc($2); })

1
เยี่ยมมากฉันจะหาข้อมูลเพิ่มเติมเกี่ยวกับเรื่องนี้ได้ที่ไหน
quano


11
เย็น. เพื่อชี้แจง: $1และ$2เป็นชื่อพารามิเตอร์ที่ผู้ใช้เลือกที่นี่ (เลือกที่จะเลียนแบบสัญลักษณ์ backreference); ที่ - แตกต่างกัน! - จำนวนพารามิเตอร์เหล่านี้สอดคล้องกับจำนวนกลุ่มการดักจับใน regex
mklement0

34

ส่งผ่านฟังก์ชันเป็นอาร์กิวเมนต์ที่สองไปที่replace:

str = str.replace(/(\$)([a-z]+)/gi, myReplace);

function myReplace(str, group1, group2) {
    return "+" + group2 + "+";
}

ความสามารถนี้ได้รับรอบตั้งแต่ Javascript 1.3 ตามmozilla.org


2

การใช้ ESNext เป็นการแทนที่ลิงก์จำลอง แต่เพียงเพื่อแสดงให้เห็นว่ามันทำงานอย่างไร:

let text = 'Visit http://lovecats.com/new-posts/ and https://lovedogs.com/best-dogs NOW !';

text = text.replace(/(https?:\/\/[^ ]+)/g, (match, link) => {
  // remove ending slash if there is one
  link = link.replace(/\/?$/, '');
  
  return `<a href="${link}" target="_blank">${link.substr(link.lastIndexOf('/') +1)}</a>`;
});

document.body.innerHTML = text;


0

หมายเหตุ:คำตอบก่อนหน้าไม่มีรหัสบางส่วน ตอนนี้ได้รับการแก้ไขแล้ว + ตัวอย่าง


ฉันต้องการสิ่งที่ยืดหยุ่นกว่านี้เล็กน้อยสำหรับการแทนที่ regex เพื่อถอดรหัส Unicode ในข้อมูล JSON ขาเข้าของฉัน:

var text = "some string with an encoded '&#115;' in it";

text.replace(/&#(\d+);/g, function() {
  return String.fromCharCode(arguments[1]);
});

// "some string with an encoded 's' in it"

0

หากคุณมีการอ้างอิงย้อนกลับจำนวนตัวแปรจำนวนอาร์กิวเมนต์ (และสถานที่) จะเป็นตัวแปรด้วย MDN เว็บเอกสารอธิบายไวยากรณ์ follwing สำหรับ sepcifing ฟังก์ชั่นเป็นอาร์กิวเมนต์ทดแทน:

function replacer(match[, p1[, p2[, p...]]], offset, string)

ตัวอย่างเช่นใช้นิพจน์ทั่วไปเหล่านี้:

var searches = [
    'test([1-3]){1,3}',  // 1 backreference
    '([Ss]ome) ([A-z]+) chars',  // 2 backreferences
    '([Mm][a@]ny) ([Mm][0o]r[3e]) ([Ww][0o]rd[5s])'  // 3 backreferences
];
for (var i in searches) {
    "Some string chars and many m0re w0rds in this test123".replace(
        new RegExp(
            searches[i]
            function(...args) {
                var match = args[0];
                var backrefs = args.slice(1, args.length - 2);
                // will be: ['Some', 'string'], ['many', 'm0re', 'w0rds'], ['123']
                var offset = args[args.length - 2];
                var string = args[args.length - 1];
            }
        )
    );
}

คุณไม่สามารถใช้ตัวแปร 'อาร์กิวเมนต์' ได้ที่นี่เนื่องจากเป็นประเภทArgumentsและไม่มีประเภทArrayดังนั้นจึงไม่มีslice()วิธีการ

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.