2013-02-13 13 views
10

मैं एक स्ट्रिंग जावास्क्रिप्ट के साथ regex का उपयोग करने से सभी संभावित मिलान प्राप्त करने के लिए कोशिश कर रहा हूँ हर संभव मिलान खोजें। ऐसा प्रतीत होता है कि ऐसा करने की मेरी विधि स्ट्रिंग के उन हिस्सों से मेल नहीं खा रही है जो पहले ही मेल खा चुके हैं।जावास्क्रिप्ट Regex - यहां तक ​​कि पहले से ही कब्जा कर लिया से मेल खाता है

चर:

var string = 'A1B1Y:A1B2Y:A1B3Y:A1B4Z:A1B5Y:A1B6Y:A1B7Y:A1B8Z:A1B9Y:A1B10Y:A1B11Y'; 

var reg = /A[0-9]+B[0-9]+Y:A[0-9]+B[0-9]+Y/g; 

कोड:

var match = string.match(reg); 

सभी मिलान परिणाम मैं:

A1B1Y:A1B2Y 
A1B5Y:A1B6Y 
A1B9Y:A1B10Y 

मेल खाने वाले परिणाम मैं चाहता हूँ:

A1B1Y:A1B2Y 
A1B2Y:A1B3Y 
A1B5Y:A1B6Y 
A1B6Y:A1B7Y 
A1B9Y:A1B10Y 
A1B10Y:A1B11Y 

मेरे सिर में, मैं A1B1Y:A1B2YA1B2Y:A1B3Y के साथ एक मैच होने के लिए चाहता हूं, भले ही A1B2Y स्ट्रिंग में दो मैचों का हिस्सा बनने की आवश्यकता होगी।

+0

एक लुकहेड आपको वह मैच मिलेगा जो आप चाहते हैं, लेकिन दुर्भाग्य से यह लुकहेड का हिस्सा वापस नहीं लौटाता है। मुझे जावास्क्रिप्ट के साथ लुकहेड कैप्चर करने का कोई तरीका नहीं मिला है। शायद वहाँ है, पता नहीं है। लुकहेड के साथ आपका रेगेक्स होगा: var reg =/a [0-9] + बी [0-9] + वाई (? =: ए [0-9] + बी [0-9] + वाई)/जी; – Someone

+0

@ मंट्रियूर: मेरा उत्तर देखें ... – nhahtdh

+0

शायद 'string.split (": ") 'और फिर सरणी पर लूपिंग आपको बेहतर परिणाम दे सकता है। – Bergi

उत्तर

20

अपने रेगेक्स को संशोधित किए बिना, आप .exec का उपयोग करके प्रत्येक मैच के बाद मैच के दूसरे भाग की शुरुआत में मिलान शुरू करने के लिए सेट कर सकते हैं और रेगेक्स ऑब्जेक्ट की lastIndex संपत्ति का उपयोग कर सकते हैं।

var string = 'A1B1Y:A1B2Y:A1B3Y:A1B4Z:A1B5Y:A1B6Y:A1B7Y:A1B8Z:A1B9Y:A1B10Y:A1B11Y'; 
var reg = /A[0-9]+B[0-9]+Y:A[0-9]+B[0-9]+Y/g; 
var matches = [], found; 
while (found = reg.exec(string)) { 
    matches.push(found[0]); 
    reg.lastIndex -= found[0].split(':')[1].length; 
} 

console.log(matches); 
//["A1B1Y:A1B2Y", "A1B2Y:A1B3Y", "A1B5Y:A1B6Y", "A1B6Y:A1B7Y", "A1B9Y:A1B10Y", "A1B10Y:A1B11Y"] 

Demo


Bergi की टिप्पणी के अनुसार, आप भी आखिरी मैच के सूचकांक मिलता है और 1 से यह भी वृद्धि कर सकते हैं, तो यह बजाय बाद मैच की दूसरी छमाही से मिलान करने के लिए शुरू करने की

reg.lastIndex = found.index+1; 

Demo

:, यह बाद प्रत्येक मैच के दूसरे चरित्र से मिलान करने के प्रयास शुरू कर देंगे

अंतिम परिणाम वही है। हालांकि, बर्गी के अपडेट में थोड़ा कम कोड है और थोड़ा faster करता है। =]

+0

काम किया, धन्यवाद! –

+2

अच्छा, यह लुकहेड, कैप्चरिंग ग्रुप इत्यादि से बेहतर है। बीटीडब्ल्यू, 'reg.lastIndex = found.index + 1;' पर्याप्त होना चाहिए और इसे अभिव्यक्ति-अज्ञेय – Bergi

+0

@ विनीकेंट कोई समस्या नहीं है। '=]' ऊपर/नीचे तीरों के नीचे वी को चिह्नित करें ताकि इसे आपके लिए काम करने के लिए स्वीकार किया जा सके। ओह धन्यवाद बर्गी, उस संपत्ति के बारे में पता नहीं था। 'x]' –

4

आप match से सीधा परिणाम नहीं मिल सकता है, लेकिन यह RegExp.exec के माध्यम से और regex के लिए कुछ संशोधन के साथ परिणाम उपज के लिए संभव है:

var regex = /A[0-9]+B[0-9]+Y(?=(:A[0-9]+B[0-9]+Y))/g; 
var input = 'A1B1Y:A1B2Y:A1B3Y:A1B4Z:A1B5Y:A1B6Y:A1B7Y:A1B8Z:A1B9Y:A1B10Y:A1B11Y' 
var arr; 
var results = []; 

while ((arr = regex.exec(input)) !== null) { 
    results.push(arr[0] + arr[1]); 
} 

मैं शून्य चौड़ाई सकारात्मक लुक-आगे इस्तेमाल किया पाठ का उपभोग न करने के लिए (?=pattern), ताकि ओवरलैपिंग भाग को रीमेच किया जा सके। ,

var input = 'A1B1Y:A1B2Y:A1B3Y:A1B4Z:A1B5Y:A1B6Y:A1B7Y:A1B8Z:A1B9Y:A1B10Y:A1B11Y' 
var results = []; 

input.replace(/A[0-9]+B[0-9]+Y(?=(:A[0-9]+B[0-9]+Y))/g, function ($0, $1) { 
    results.push($0 + $1); 
    return ''; 
}); 

लेकिन जब से यह replace है, यह अतिरिक्त बेकार प्रतिस्थापन काम करता है:

वास्तव में, यह replace विधि दुरुपयोग के लिए एक ही परिणाम प्राप्त करने के लिए संभव है।

+0

यह भी काम किया, धन्यवाद! –

3

दुर्भाग्य से, यह एक string.match जितना आसान नहीं है।

कारण यह है कि आप ओवरलैपिंग मैचों को चाहते हैं, जो /g ध्वज आपको नहीं देता है।

आप अग्रदर्शी इस्तेमाल कर सकते हैं:

var re = /A\d+B\d+Y(?=:A\d+B\d+Y)/g; 

लेकिन अब आपको मिलेगा:

string.match(re); // ["A1B1Y", "A1B2Y", "A1B5Y", "A1B6Y", "A1B9Y", "A1B10Y"] 

कारण यह है कि अग्रदर्शी शून्य चौड़ाई है, जिसका अर्थ यह सिर्फ का कहना है कि पैटर्न के बाद आप क्या आता है कि क्या है मैच करने की कोशिश कर रहे हैं या नहीं; इसमें इसे मैच में शामिल नहीं किया गया है।

आप जो चाहते हैं उसे आजमाने और पकड़ने के लिए exec का उपयोग कर सकते हैं। एक regex /g झंडा है, तो आप exec बार-बार चलाने के सभी मैचों प्राप्त करने के लिए कर सकते हैं:

// using re from above to get the overlapping matches 

var m; 
var matches = []; 
var re2 = /A\d+B\d+Y:A\d+B\d+Y/g; // make another regex to get what we need 

while ((m = re.exec(string)) !== null) { 
    // m is a match object, which has the index of the current match 
    matches.push(string.substring(m.index).match(re2)[0]); 
} 

matches == [ 
    "A1B1Y:A1B2Y", 
    "A1B2Y:A1B3Y", 
    "A1B5Y:A1B6Y", 
    "A1B6Y:A1B7Y", 
    "A1B9Y:A1B10Y", 
    "A1B10Y:A1B11Y" 
]; 

Here's a fiddle of this in action। परिणाम देखने के लिए

वैकल्पिक रूप से सांत्वना खोलें, आप परिणामी सरणी के माध्यम से तो पाश : पर मूल स्ट्रिंग विभाजित नहीं कर सके, लोगों से मेल खाते हैं कि जब array[i] और array[i+1] दोनों मैच की तरह आप चाहते हैं बाहर खींच रहा है।

संबंधित मुद्दे