Reputation: 159
I have a text file, each line is a string.
The most extreme could look like this:
A01B01C01D100E500F100.00G100.00H100.00
A little information about possibilities:
Another example of the data:
A01B400C62.578D77.297
C62.409D77.222
C62.259D77.113
C62.135D76.975
C62.042D76.815
C61.985D76.638
C61.973D76.529
A03B10000
A0C62.760 D77.336
A0E3.000
A01F400E0
A01B400E-0.100
What I would like to do is split the string at each letter, and taking all of the numbers until the next letter. With results like so:
A01, B01, C01, D100, E500, F100.00, G100.00, H100.00
I have tried a bunch of things, and the closest I have gotten is this
dicedLine = myLine.split(/[ABCDEFGH]/)
This gives me CLOSE to what I want, except I have found that if you have a string that does not include one of those letters in the search, then the results are not what I am after.
For example a line like this:
A30
Will give me results like this:
["", "30"]
Where I would really want results like this:
["A30", "", "", "", "", "", "", ""]
Any ideas are appreciated!
Upvotes: 1
Views: 1676
Reputation: 20228
Where I would really want results like this:
["A30", "", "", "", "", "", "", ""]
If the letters are ordered, this is easily accomplished by capturing each letter + digits in its own group as follows:
let re = /(A[^A-Z]+)?(B[^A-Z]+)?(C[^A-Z]+)?(D[^A-Z]+)?(E[^A-Z]+)?(F[^A-Z]+)?(G[^A-Z]+)?(H[^A-Z]+)?/;
console.log(re.exec("A01B01C01D100E500F100.00G100.00H100.00").slice(1));
console.log(re.exec("C30").slice(1));
Non-matching groups produce an undefined
array entry. Those can easily be mapped to empty strings if desired.
The letters are not always in order
You would need to replace the individual letters in the given regexp with their generic group [A-Z]
.
However, your question is ambiguous about unordered letters. Shall "C30B30"
result in ["", "B30", "C30", "", "", "", "", ""]
? Or ["B30", "C30", "", "", "", "", "", ""]
? We can't answer that part of the question without more specifications.
Upvotes: 0
Reputation: 147363
You can do this fairly easily with match rather than split. It's a simper regular expression so likely more compatible. Just beware that if no matches are found, it returns null rather than an empty array.
var data = [
'A01B400C62.578D77.297',
'C62.409D77.222',
'C62.259D77.113',
'C62.135D76.975',
'C62.042D76.815',
'C61.985D76.638',
'C61.973D76.529',
'A03B10000',
'A0C62.760 D77.336',
'A0E3.000',
'A01F400E0',
'A01B400E-0.100'
];
var result = data.map(s => s.match(/[a-z][^a-z]+/gi));
console.log(result);
Upvotes: 0
Reputation: 21161
You can use positive lookahead to assert that a particular character exists, without actually consuming it:
codes = [
"A01B400C62.578D77.297",
"C62.409D77.222",
"C62.259D77.113",
"C62.135D76.975",
"C62.042D76.815",
"C61.985D76.638",
"C61.973D76.529",
"A03B10000",
"A0C62.760 D77.336",
"A0E3.000",
"A01F400E0",
"A01B400E-0.100",
];
console.log(codes.map(code => code.split(/ *(?=[A-Z])/)));
Note I also added *
to remove the spaces, if any.
Upvotes: 3