2017-01-07 10 views
6

Ich möchte eine Zeichenfolge durch Kommas getrennt werden, aber nicht, wenn sie in Klammern sind.Durch Kommas getrennt, aber nicht in Klammern mit regexp

Zum Beispiel:

"[1, '15', [false]], [[], 'sup']" 

würde aufgeteilt in

[ 
    "[1, '15', [false]]", 
    "[[], 'sup']" 
] 

ich /\,(?=(.*\[.*\])*.*\]{1})/ für meinen regexp habe versucht, meine Logik Spiel Kommas, die nicht durch eine gerade Anzahl von ‚gefolgt werden [ ] 'mit irgendwelchen Zeichen dazwischen und außerhalb gefolgt von einem'] '.

+0

Sind die Array-Literale zunächst: Sie könnten einen kleinen Parser schreiben wollen Beispiel gültige Arrays? – guest271314

+0

@ guest271314: OP sagt, sie haben eine * Zeichenkette *, also vermutlich der Inhalt einer Zeichenkette. –

+0

@FelixKling _ "aber nicht, wenn sie innerhalb eines Array-Elements sind" _ Gegebene Anfangszeichenfolge, wie man bestimmt, welches Feldelement ist? Split bei Komma um ']], [['? – guest271314

Antwort

2

Wenn erwartete Ergebnis zwei Strings sind, unabhängig davon, ob oder nicht Strings sind parseable als javascript Objekt oder gültige JSON Sie Array.prototype.reduce() verwenden können, String.prototype.split(), String.prototype.replace()

var str = "[1, '15', [false]], [[], 'sup']"; 
 

 
var res = str.split(/,/).reduce((arr, text) => { 
 

 
    text = text.trim(); 
 

 
    if (arr.length === 0) { 
 
    arr.push([]); 
 
    } 
 
    
 
    if (/^\[/.test(text) && !/\]$/.test(text)) { 
 
    arr[arr.length === 1 ? 0 : arr.length - 1].push(text.slice(1)); 
 
    return arr 
 
    } 
 
    
 
    if (!/^\[/.test(text) && /\]$/.test(text)) { 
 
    arr[arr.length === 1 ? 0 : arr.length - 1].push(text.slice(0, -1)); 
 
    return arr 
 
    } 
 

 
    if (!/^\[/.test(text) && !/\]$/.test(text) 
 
     || /^\[/.test(text) && /\]{2}$/.test(text) 
 
     || !/\[|\]/.test(text)) { 
 
     arr[arr.length === 1 ? 0 : arr.length - 1].push(text); 
 
    return arr 
 
    } 
 
    
 
    if (/^\[{2}/.test(text) && /\]$/.test(text)) { 
 
    arr[arr.length - 1].push(text); 
 
    return arr 
 
    } 
 

 
    return arr 
 

 
}, []); 
 

 
var strs = `[${res.join()}]`.replace(/"/g, "").split(/,(?=\[{2})|"(?=")/); 
 

 
console.log(`str1:${strs[0]}\nstr2:${strs[1]}`);

0

Wenn Zeichenfolge richtig ist Array-artige Zeichenfolge ... vielleicht ist es auch einen Versuch wert:

var regex = /(\[.*?\]\])|(\[\[.*?\]$)|(\[(.*?)\])|(,)/gm; 

var regex = /(\[.*?\]\])|(\[\[.*?\]$)|(\[(.*?)\])|(,)/gm; 
 
str = "[1, '15', [false]], [[], 'sup']"; 
 
/*str="[1, [30] [false][,]], [[]false, 'sup'[]]"; 
 
str="[[] []], [1,4,5[8]]"; 
 
str="[[1,2,3],[3,6,7]],[[],566,[]]"; 
 
str="[[],[]],['duh,[],'buh',[]]"; 
 

 
str="[1,2,3],[5,'ggg','h']"*/ 
 

 

 
arr=[]; 
 
while ((matches = regex.exec(str)) !== null) { 
 
if(matches[0]!==',') 
 
arr.push(matches[0]); 
 

 
    
 
} 
 

 
console.log(arr);

Also, im Grunde passen alternative Gruppen, Schleife durch Ergebnisse, halten nicht-Komma Streichhölzer. Dies wird wahrscheinlich in einigen Fällen fehlschlagen ... sollte aber mehr getestet werden.

1

Regexp eignet sich nicht für solche Situationen, bei denen die Verschachtelung erforderlich ist.

function parse(str) { 
 
    let result = [], item = '', depth = 0; 
 

 
    function push() { if (item) result.push(item); item = ''; } 
 

 
    for (let i = 0, c; c = str[i], i < str.length; i++) { 
 
    if (!depth && c === ',') push(); 
 
    else { 
 
     item += c; 
 
     if (c === '[') depth++; 
 
     if (c === ']') depth--; 
 
    } 
 
    } 
 
    
 
    push(); 
 
    return result; 
 
} 
 
     
 
console.log(parse("[1, '15', [false]], [[], 'sup']"));

Sie diese vielleicht zwicken Räume zu behandeln um die Kommas, unausgewogene eckigen Klammern etc.

+0

Das ist wirklich nett, vielen Dank – JiniHendrix

Verwandte Themen