Is there a better way to extract information from a string?
Let's say I have an array of strings, and I need specific info from them, what would be an easy way to do that?
Suppose the array was this
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
Let's say I wanted the date extracted and saved into another array, well I could make a function like this
function extractDates(arr){
let dateRegex = /(d{1,2}/){2}d{4}/g, dates = "";
let dateArr = ;
for(let i = 0; i<arr.length; i++){
dates = /(d{1,2}/){2}d{4}/g.exec(arr[i])
dates.pop();
dateArr.push(dates);
}
return dateArr.flat();
}
Although this works, it is clunky and requires I pop() because it will return an array of arrays, ie: ["12/16/1988", "16/"], plus I need to call flat afterwards.
Another option would be to substring the strings, with a given position, where I need to know a regex pattern.
function extractDates2(arr){
let dates = ;
for(let i = 0; i<arr.length; i++){
let begin = regexIndexOf(arr[i], /(d{1,2}/){2}d{4}/g);
let end = regexIndexOf(arr[i], /[0-9] /g, begin) + 1;
dates.push(arr[i].substring(begin, end));
}
return dates;
}
And of course have a regexIndexOf function
function regexIndexOf(str, regex, start = 0){
let indexOf = str.substring(start).search(regex);
indexOf = (indexOf >= 0) ? (indexOf + start) : -1;
return indexOf;
}
Again this function also works, but it seems like an awful lot just to extract something simple. Is there an easier way to extract data into an array?
javascript
add a comment |
Let's say I have an array of strings, and I need specific info from them, what would be an easy way to do that?
Suppose the array was this
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
Let's say I wanted the date extracted and saved into another array, well I could make a function like this
function extractDates(arr){
let dateRegex = /(d{1,2}/){2}d{4}/g, dates = "";
let dateArr = ;
for(let i = 0; i<arr.length; i++){
dates = /(d{1,2}/){2}d{4}/g.exec(arr[i])
dates.pop();
dateArr.push(dates);
}
return dateArr.flat();
}
Although this works, it is clunky and requires I pop() because it will return an array of arrays, ie: ["12/16/1988", "16/"], plus I need to call flat afterwards.
Another option would be to substring the strings, with a given position, where I need to know a regex pattern.
function extractDates2(arr){
let dates = ;
for(let i = 0; i<arr.length; i++){
let begin = regexIndexOf(arr[i], /(d{1,2}/){2}d{4}/g);
let end = regexIndexOf(arr[i], /[0-9] /g, begin) + 1;
dates.push(arr[i].substring(begin, end));
}
return dates;
}
And of course have a regexIndexOf function
function regexIndexOf(str, regex, start = 0){
let indexOf = str.substring(start).search(regex);
indexOf = (indexOf >= 0) ? (indexOf + start) : -1;
return indexOf;
}
Again this function also works, but it seems like an awful lot just to extract something simple. Is there an easier way to extract data into an array?
javascript
3
Why not use array.map?
– Henry Howeson
2 days ago
@HenryHoweson.map(alone) won't work if there's more than one date in one of the input strings, eg"1 Ben Howard 12/16/1988 apple 1/10/1999 ", he'd have to flatten it afterwards
– CertainPerformance
2 days ago
1
@CertainPerformance With the regex global flag set it would work fine, also the OP doesn't appear to require that.
– Henry Howeson
2 days ago
@HenryHoweson Just using the global flag doesn't allow for (concise) extraction of matches from multiple strings into a single array, I thought? What code are you thinking of?
– CertainPerformance
2 days ago
add a comment |
Let's say I have an array of strings, and I need specific info from them, what would be an easy way to do that?
Suppose the array was this
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
Let's say I wanted the date extracted and saved into another array, well I could make a function like this
function extractDates(arr){
let dateRegex = /(d{1,2}/){2}d{4}/g, dates = "";
let dateArr = ;
for(let i = 0; i<arr.length; i++){
dates = /(d{1,2}/){2}d{4}/g.exec(arr[i])
dates.pop();
dateArr.push(dates);
}
return dateArr.flat();
}
Although this works, it is clunky and requires I pop() because it will return an array of arrays, ie: ["12/16/1988", "16/"], plus I need to call flat afterwards.
Another option would be to substring the strings, with a given position, where I need to know a regex pattern.
function extractDates2(arr){
let dates = ;
for(let i = 0; i<arr.length; i++){
let begin = regexIndexOf(arr[i], /(d{1,2}/){2}d{4}/g);
let end = regexIndexOf(arr[i], /[0-9] /g, begin) + 1;
dates.push(arr[i].substring(begin, end));
}
return dates;
}
And of course have a regexIndexOf function
function regexIndexOf(str, regex, start = 0){
let indexOf = str.substring(start).search(regex);
indexOf = (indexOf >= 0) ? (indexOf + start) : -1;
return indexOf;
}
Again this function also works, but it seems like an awful lot just to extract something simple. Is there an easier way to extract data into an array?
javascript
Let's say I have an array of strings, and I need specific info from them, what would be an easy way to do that?
Suppose the array was this
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
Let's say I wanted the date extracted and saved into another array, well I could make a function like this
function extractDates(arr){
let dateRegex = /(d{1,2}/){2}d{4}/g, dates = "";
let dateArr = ;
for(let i = 0; i<arr.length; i++){
dates = /(d{1,2}/){2}d{4}/g.exec(arr[i])
dates.pop();
dateArr.push(dates);
}
return dateArr.flat();
}
Although this works, it is clunky and requires I pop() because it will return an array of arrays, ie: ["12/16/1988", "16/"], plus I need to call flat afterwards.
Another option would be to substring the strings, with a given position, where I need to know a regex pattern.
function extractDates2(arr){
let dates = ;
for(let i = 0; i<arr.length; i++){
let begin = regexIndexOf(arr[i], /(d{1,2}/){2}d{4}/g);
let end = regexIndexOf(arr[i], /[0-9] /g, begin) + 1;
dates.push(arr[i].substring(begin, end));
}
return dates;
}
And of course have a regexIndexOf function
function regexIndexOf(str, regex, start = 0){
let indexOf = str.substring(start).search(regex);
indexOf = (indexOf >= 0) ? (indexOf + start) : -1;
return indexOf;
}
Again this function also works, but it seems like an awful lot just to extract something simple. Is there an easier way to extract data into an array?
javascript
javascript
asked 2 days ago
Travis
667510
667510
3
Why not use array.map?
– Henry Howeson
2 days ago
@HenryHoweson.map(alone) won't work if there's more than one date in one of the input strings, eg"1 Ben Howard 12/16/1988 apple 1/10/1999 ", he'd have to flatten it afterwards
– CertainPerformance
2 days ago
1
@CertainPerformance With the regex global flag set it would work fine, also the OP doesn't appear to require that.
– Henry Howeson
2 days ago
@HenryHoweson Just using the global flag doesn't allow for (concise) extraction of matches from multiple strings into a single array, I thought? What code are you thinking of?
– CertainPerformance
2 days ago
add a comment |
3
Why not use array.map?
– Henry Howeson
2 days ago
@HenryHoweson.map(alone) won't work if there's more than one date in one of the input strings, eg"1 Ben Howard 12/16/1988 apple 1/10/1999 ", he'd have to flatten it afterwards
– CertainPerformance
2 days ago
1
@CertainPerformance With the regex global flag set it would work fine, also the OP doesn't appear to require that.
– Henry Howeson
2 days ago
@HenryHoweson Just using the global flag doesn't allow for (concise) extraction of matches from multiple strings into a single array, I thought? What code are you thinking of?
– CertainPerformance
2 days ago
3
3
Why not use array.map?
– Henry Howeson
2 days ago
Why not use array.map?
– Henry Howeson
2 days ago
@HenryHoweson
.map (alone) won't work if there's more than one date in one of the input strings, eg "1 Ben Howard 12/16/1988 apple 1/10/1999 ", he'd have to flatten it afterwards– CertainPerformance
2 days ago
@HenryHoweson
.map (alone) won't work if there's more than one date in one of the input strings, eg "1 Ben Howard 12/16/1988 apple 1/10/1999 ", he'd have to flatten it afterwards– CertainPerformance
2 days ago
1
1
@CertainPerformance With the regex global flag set it would work fine, also the OP doesn't appear to require that.
– Henry Howeson
2 days ago
@CertainPerformance With the regex global flag set it would work fine, also the OP doesn't appear to require that.
– Henry Howeson
2 days ago
@HenryHoweson Just using the global flag doesn't allow for (concise) extraction of matches from multiple strings into a single array, I thought? What code are you thinking of?
– CertainPerformance
2 days ago
@HenryHoweson Just using the global flag doesn't allow for (concise) extraction of matches from multiple strings into a single array, I thought? What code are you thinking of?
– CertainPerformance
2 days ago
add a comment |
4 Answers
4
active
oldest
votes
One option would be to join the strings by a separator that won't be matched, like ,, then just perform the global match to get an array of dates from it:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr
.join(',')
.match(/(d{1,2}/){2}d{4}/g);
console.log(result);
1
Works great, and is very concise and easy to reason about.
– Travis
2 days ago
4
This solution appears to be the quickest: jsben.ch/w9geK additionally it has the advantage that it handles array elements without dates (doesn't create null values in the array), do keep in mind however that if you are trying to get the date of a specific element by its' index based on the original array then it may not line up if some elements don't have dates
– Henry Howeson
2 days ago
1
@HenryHoweson It has certain performance to it
– wscourge
2 days ago
1
This doesn't work when theinfoArris empty or none of the strings contains a date, as thenmatch()returnsnullinstead of an array. There's no reason to usejoinhere,maporflatMapare much more reasonable.
– Bergi
2 days ago
add a comment |
One approach could be using map() over the elements of the array applying the match on each element, and finally call flat() to get the desired result:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g)).flat();
console.log(result);Alternatively, you could use flatMap():
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g));
console.log(result);Also, if you need to remove null values from the final array in the case there are strings without dates, you can apply filter(), like this:
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g))
.flat()
.filter(date => date !== null);
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null);
Example (taking into consideration some conflicting data)
let infoArr = [
"1 Ben Howard 12/16/1988 apple 10/22/1922",
"2 James Smith orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/19075 peach",
"5 Doug Jones 11/10-1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null); /* or filter(date => date) */
console.log(result);
2
You will end up withnullvalues in the array if any of the lines don't contain dates.
– Mark Meyer
2 days ago
Thanks for feedback, going to think a workaround for that...
– Shidersz
2 days ago
1
@Shidersz add .filter((e) => {return e}) to the end
– Henry Howeson
2 days ago
Yeah, thank you, I was writing about that, but I used a more readable syntax
– Shidersz
2 days ago
2
Also, keep in mind thatflatandflatMapare still currently "experimental" and subject to change.
– Drew Reese
2 days ago
add a comment |
Although this works, it is clunky and requires
pop()because it will return an array of arrays, ie:["12/16/1988", "16/"], plus I need to callflatafterwards.
The regex exec method always has its match in the 0 property (assuming that it matches at all), you can just access that and push it to your array:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
function extractDates(arr){
const dateRegex = /(d{1,2}/){2}d{4}/g;
const dateArr = ;
for (const str of arr){
const date = /(d{1,2}/){2}d{4}/g.exec(str);
dateArr.push(date[0]);
}
return dateArr;
}
console.log(extractDates(infoArr));(of course you could also do the same in a map callback)
add a comment |
You can use reduce() rather than the loops to pair down the code. Just be careful to keep the null out of the array if there is no match.
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
let regex = /(d{1,2}/){2}d{4}/g
let dates = infoArr.reduce((arr, s) => arr.concat(s.match(regex) || ) , )
console.log(dates)add a comment |
Your Answer
StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");
StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "1"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);
StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});
function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});
}
});
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f54000799%2fis-there-a-better-way-to-extract-information-from-a-string%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
4 Answers
4
active
oldest
votes
4 Answers
4
active
oldest
votes
active
oldest
votes
active
oldest
votes
One option would be to join the strings by a separator that won't be matched, like ,, then just perform the global match to get an array of dates from it:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr
.join(',')
.match(/(d{1,2}/){2}d{4}/g);
console.log(result);
1
Works great, and is very concise and easy to reason about.
– Travis
2 days ago
4
This solution appears to be the quickest: jsben.ch/w9geK additionally it has the advantage that it handles array elements without dates (doesn't create null values in the array), do keep in mind however that if you are trying to get the date of a specific element by its' index based on the original array then it may not line up if some elements don't have dates
– Henry Howeson
2 days ago
1
@HenryHoweson It has certain performance to it
– wscourge
2 days ago
1
This doesn't work when theinfoArris empty or none of the strings contains a date, as thenmatch()returnsnullinstead of an array. There's no reason to usejoinhere,maporflatMapare much more reasonable.
– Bergi
2 days ago
add a comment |
One option would be to join the strings by a separator that won't be matched, like ,, then just perform the global match to get an array of dates from it:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr
.join(',')
.match(/(d{1,2}/){2}d{4}/g);
console.log(result);
1
Works great, and is very concise and easy to reason about.
– Travis
2 days ago
4
This solution appears to be the quickest: jsben.ch/w9geK additionally it has the advantage that it handles array elements without dates (doesn't create null values in the array), do keep in mind however that if you are trying to get the date of a specific element by its' index based on the original array then it may not line up if some elements don't have dates
– Henry Howeson
2 days ago
1
@HenryHoweson It has certain performance to it
– wscourge
2 days ago
1
This doesn't work when theinfoArris empty or none of the strings contains a date, as thenmatch()returnsnullinstead of an array. There's no reason to usejoinhere,maporflatMapare much more reasonable.
– Bergi
2 days ago
add a comment |
One option would be to join the strings by a separator that won't be matched, like ,, then just perform the global match to get an array of dates from it:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr
.join(',')
.match(/(d{1,2}/){2}d{4}/g);
console.log(result);One option would be to join the strings by a separator that won't be matched, like ,, then just perform the global match to get an array of dates from it:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr
.join(',')
.match(/(d{1,2}/){2}d{4}/g);
console.log(result);let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr
.join(',')
.match(/(d{1,2}/){2}d{4}/g);
console.log(result);let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr
.join(',')
.match(/(d{1,2}/){2}d{4}/g);
console.log(result);answered 2 days ago
CertainPerformance
76.9k143862
76.9k143862
1
Works great, and is very concise and easy to reason about.
– Travis
2 days ago
4
This solution appears to be the quickest: jsben.ch/w9geK additionally it has the advantage that it handles array elements without dates (doesn't create null values in the array), do keep in mind however that if you are trying to get the date of a specific element by its' index based on the original array then it may not line up if some elements don't have dates
– Henry Howeson
2 days ago
1
@HenryHoweson It has certain performance to it
– wscourge
2 days ago
1
This doesn't work when theinfoArris empty or none of the strings contains a date, as thenmatch()returnsnullinstead of an array. There's no reason to usejoinhere,maporflatMapare much more reasonable.
– Bergi
2 days ago
add a comment |
1
Works great, and is very concise and easy to reason about.
– Travis
2 days ago
4
This solution appears to be the quickest: jsben.ch/w9geK additionally it has the advantage that it handles array elements without dates (doesn't create null values in the array), do keep in mind however that if you are trying to get the date of a specific element by its' index based on the original array then it may not line up if some elements don't have dates
– Henry Howeson
2 days ago
1
@HenryHoweson It has certain performance to it
– wscourge
2 days ago
1
This doesn't work when theinfoArris empty or none of the strings contains a date, as thenmatch()returnsnullinstead of an array. There's no reason to usejoinhere,maporflatMapare much more reasonable.
– Bergi
2 days ago
1
1
Works great, and is very concise and easy to reason about.
– Travis
2 days ago
Works great, and is very concise and easy to reason about.
– Travis
2 days ago
4
4
This solution appears to be the quickest: jsben.ch/w9geK additionally it has the advantage that it handles array elements without dates (doesn't create null values in the array), do keep in mind however that if you are trying to get the date of a specific element by its' index based on the original array then it may not line up if some elements don't have dates
– Henry Howeson
2 days ago
This solution appears to be the quickest: jsben.ch/w9geK additionally it has the advantage that it handles array elements without dates (doesn't create null values in the array), do keep in mind however that if you are trying to get the date of a specific element by its' index based on the original array then it may not line up if some elements don't have dates
– Henry Howeson
2 days ago
1
1
@HenryHoweson It has certain performance to it
– wscourge
2 days ago
@HenryHoweson It has certain performance to it
– wscourge
2 days ago
1
1
This doesn't work when the
infoArr is empty or none of the strings contains a date, as then match() returns null instead of an array. There's no reason to use join here, map or flatMap are much more reasonable.– Bergi
2 days ago
This doesn't work when the
infoArr is empty or none of the strings contains a date, as then match() returns null instead of an array. There's no reason to use join here, map or flatMap are much more reasonable.– Bergi
2 days ago
add a comment |
One approach could be using map() over the elements of the array applying the match on each element, and finally call flat() to get the desired result:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g)).flat();
console.log(result);Alternatively, you could use flatMap():
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g));
console.log(result);Also, if you need to remove null values from the final array in the case there are strings without dates, you can apply filter(), like this:
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g))
.flat()
.filter(date => date !== null);
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null);
Example (taking into consideration some conflicting data)
let infoArr = [
"1 Ben Howard 12/16/1988 apple 10/22/1922",
"2 James Smith orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/19075 peach",
"5 Doug Jones 11/10-1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null); /* or filter(date => date) */
console.log(result);
2
You will end up withnullvalues in the array if any of the lines don't contain dates.
– Mark Meyer
2 days ago
Thanks for feedback, going to think a workaround for that...
– Shidersz
2 days ago
1
@Shidersz add .filter((e) => {return e}) to the end
– Henry Howeson
2 days ago
Yeah, thank you, I was writing about that, but I used a more readable syntax
– Shidersz
2 days ago
2
Also, keep in mind thatflatandflatMapare still currently "experimental" and subject to change.
– Drew Reese
2 days ago
add a comment |
One approach could be using map() over the elements of the array applying the match on each element, and finally call flat() to get the desired result:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g)).flat();
console.log(result);Alternatively, you could use flatMap():
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g));
console.log(result);Also, if you need to remove null values from the final array in the case there are strings without dates, you can apply filter(), like this:
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g))
.flat()
.filter(date => date !== null);
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null);
Example (taking into consideration some conflicting data)
let infoArr = [
"1 Ben Howard 12/16/1988 apple 10/22/1922",
"2 James Smith orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/19075 peach",
"5 Doug Jones 11/10-1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null); /* or filter(date => date) */
console.log(result);
2
You will end up withnullvalues in the array if any of the lines don't contain dates.
– Mark Meyer
2 days ago
Thanks for feedback, going to think a workaround for that...
– Shidersz
2 days ago
1
@Shidersz add .filter((e) => {return e}) to the end
– Henry Howeson
2 days ago
Yeah, thank you, I was writing about that, but I used a more readable syntax
– Shidersz
2 days ago
2
Also, keep in mind thatflatandflatMapare still currently "experimental" and subject to change.
– Drew Reese
2 days ago
add a comment |
One approach could be using map() over the elements of the array applying the match on each element, and finally call flat() to get the desired result:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g)).flat();
console.log(result);Alternatively, you could use flatMap():
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g));
console.log(result);Also, if you need to remove null values from the final array in the case there are strings without dates, you can apply filter(), like this:
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g))
.flat()
.filter(date => date !== null);
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null);
Example (taking into consideration some conflicting data)
let infoArr = [
"1 Ben Howard 12/16/1988 apple 10/22/1922",
"2 James Smith orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/19075 peach",
"5 Doug Jones 11/10-1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null); /* or filter(date => date) */
console.log(result);One approach could be using map() over the elements of the array applying the match on each element, and finally call flat() to get the desired result:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g)).flat();
console.log(result);Alternatively, you could use flatMap():
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g));
console.log(result);Also, if you need to remove null values from the final array in the case there are strings without dates, you can apply filter(), like this:
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g))
.flat()
.filter(date => date !== null);
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null);
Example (taking into consideration some conflicting data)
let infoArr = [
"1 Ben Howard 12/16/1988 apple 10/22/1922",
"2 James Smith orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/19075 peach",
"5 Doug Jones 11/10-1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null); /* or filter(date => date) */
console.log(result);let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g)).flat();
console.log(result);let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.map(o => o.match(/(d{1,2}/){2}d{4}/g)).flat();
console.log(result);let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g));
console.log(result);let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g));
console.log(result);let infoArr = [
"1 Ben Howard 12/16/1988 apple 10/22/1922",
"2 James Smith orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/19075 peach",
"5 Doug Jones 11/10-1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null); /* or filter(date => date) */
console.log(result);let infoArr = [
"1 Ben Howard 12/16/1988 apple 10/22/1922",
"2 James Smith orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/19075 peach",
"5 Doug Jones 11/10-1975 peach"
];
const result = infoArr.flatMap(o => o.match(/(d{1,2}/){2}d{4}/g))
.filter(date => date !== null); /* or filter(date => date) */
console.log(result);edited yesterday
answered 2 days ago
Shidersz
3,8412528
3,8412528
2
You will end up withnullvalues in the array if any of the lines don't contain dates.
– Mark Meyer
2 days ago
Thanks for feedback, going to think a workaround for that...
– Shidersz
2 days ago
1
@Shidersz add .filter((e) => {return e}) to the end
– Henry Howeson
2 days ago
Yeah, thank you, I was writing about that, but I used a more readable syntax
– Shidersz
2 days ago
2
Also, keep in mind thatflatandflatMapare still currently "experimental" and subject to change.
– Drew Reese
2 days ago
add a comment |
2
You will end up withnullvalues in the array if any of the lines don't contain dates.
– Mark Meyer
2 days ago
Thanks for feedback, going to think a workaround for that...
– Shidersz
2 days ago
1
@Shidersz add .filter((e) => {return e}) to the end
– Henry Howeson
2 days ago
Yeah, thank you, I was writing about that, but I used a more readable syntax
– Shidersz
2 days ago
2
Also, keep in mind thatflatandflatMapare still currently "experimental" and subject to change.
– Drew Reese
2 days ago
2
2
You will end up with
null values in the array if any of the lines don't contain dates.– Mark Meyer
2 days ago
You will end up with
null values in the array if any of the lines don't contain dates.– Mark Meyer
2 days ago
Thanks for feedback, going to think a workaround for that...
– Shidersz
2 days ago
Thanks for feedback, going to think a workaround for that...
– Shidersz
2 days ago
1
1
@Shidersz add .filter((e) => {return e}) to the end
– Henry Howeson
2 days ago
@Shidersz add .filter((e) => {return e}) to the end
– Henry Howeson
2 days ago
Yeah, thank you, I was writing about that, but I used a more readable syntax
– Shidersz
2 days ago
Yeah, thank you, I was writing about that, but I used a more readable syntax
– Shidersz
2 days ago
2
2
Also, keep in mind that
flat and flatMap are still currently "experimental" and subject to change.– Drew Reese
2 days ago
Also, keep in mind that
flat and flatMap are still currently "experimental" and subject to change.– Drew Reese
2 days ago
add a comment |
Although this works, it is clunky and requires
pop()because it will return an array of arrays, ie:["12/16/1988", "16/"], plus I need to callflatafterwards.
The regex exec method always has its match in the 0 property (assuming that it matches at all), you can just access that and push it to your array:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
function extractDates(arr){
const dateRegex = /(d{1,2}/){2}d{4}/g;
const dateArr = ;
for (const str of arr){
const date = /(d{1,2}/){2}d{4}/g.exec(str);
dateArr.push(date[0]);
}
return dateArr;
}
console.log(extractDates(infoArr));(of course you could also do the same in a map callback)
add a comment |
Although this works, it is clunky and requires
pop()because it will return an array of arrays, ie:["12/16/1988", "16/"], plus I need to callflatafterwards.
The regex exec method always has its match in the 0 property (assuming that it matches at all), you can just access that and push it to your array:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
function extractDates(arr){
const dateRegex = /(d{1,2}/){2}d{4}/g;
const dateArr = ;
for (const str of arr){
const date = /(d{1,2}/){2}d{4}/g.exec(str);
dateArr.push(date[0]);
}
return dateArr;
}
console.log(extractDates(infoArr));(of course you could also do the same in a map callback)
add a comment |
Although this works, it is clunky and requires
pop()because it will return an array of arrays, ie:["12/16/1988", "16/"], plus I need to callflatafterwards.
The regex exec method always has its match in the 0 property (assuming that it matches at all), you can just access that and push it to your array:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
function extractDates(arr){
const dateRegex = /(d{1,2}/){2}d{4}/g;
const dateArr = ;
for (const str of arr){
const date = /(d{1,2}/){2}d{4}/g.exec(str);
dateArr.push(date[0]);
}
return dateArr;
}
console.log(extractDates(infoArr));(of course you could also do the same in a map callback)
Although this works, it is clunky and requires
pop()because it will return an array of arrays, ie:["12/16/1988", "16/"], plus I need to callflatafterwards.
The regex exec method always has its match in the 0 property (assuming that it matches at all), you can just access that and push it to your array:
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
function extractDates(arr){
const dateRegex = /(d{1,2}/){2}d{4}/g;
const dateArr = ;
for (const str of arr){
const date = /(d{1,2}/){2}d{4}/g.exec(str);
dateArr.push(date[0]);
}
return dateArr;
}
console.log(extractDates(infoArr));(of course you could also do the same in a map callback)
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
function extractDates(arr){
const dateRegex = /(d{1,2}/){2}d{4}/g;
const dateArr = ;
for (const str of arr){
const date = /(d{1,2}/){2}d{4}/g.exec(str);
dateArr.push(date[0]);
}
return dateArr;
}
console.log(extractDates(infoArr));let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
function extractDates(arr){
const dateRegex = /(d{1,2}/){2}d{4}/g;
const dateArr = ;
for (const str of arr){
const date = /(d{1,2}/){2}d{4}/g.exec(str);
dateArr.push(date[0]);
}
return dateArr;
}
console.log(extractDates(infoArr));edited 2 days ago
scraaappy
2,20621326
2,20621326
answered 2 days ago
Bergi
364k58543868
364k58543868
add a comment |
add a comment |
You can use reduce() rather than the loops to pair down the code. Just be careful to keep the null out of the array if there is no match.
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
let regex = /(d{1,2}/){2}d{4}/g
let dates = infoArr.reduce((arr, s) => arr.concat(s.match(regex) || ) , )
console.log(dates)add a comment |
You can use reduce() rather than the loops to pair down the code. Just be careful to keep the null out of the array if there is no match.
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
let regex = /(d{1,2}/){2}d{4}/g
let dates = infoArr.reduce((arr, s) => arr.concat(s.match(regex) || ) , )
console.log(dates)add a comment |
You can use reduce() rather than the loops to pair down the code. Just be careful to keep the null out of the array if there is no match.
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
let regex = /(d{1,2}/){2}d{4}/g
let dates = infoArr.reduce((arr, s) => arr.concat(s.match(regex) || ) , )
console.log(dates)You can use reduce() rather than the loops to pair down the code. Just be careful to keep the null out of the array if there is no match.
let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
let regex = /(d{1,2}/){2}d{4}/g
let dates = infoArr.reduce((arr, s) => arr.concat(s.match(regex) || ) , )
console.log(dates)let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
let regex = /(d{1,2}/){2}d{4}/g
let dates = infoArr.reduce((arr, s) => arr.concat(s.match(regex) || ) , )
console.log(dates)let infoArr = [
"1 Ben Howard 12/16/1988 apple",
"2 James Smith 1/10/1999 orange",
"3 Andy Bloss 10/25/1956 apple",
"4 Carrie Walters 8/20/1975 peach",
"5 Doug Jones 11/10/1975 peach"
];
let regex = /(d{1,2}/){2}d{4}/g
let dates = infoArr.reduce((arr, s) => arr.concat(s.match(regex) || ) , )
console.log(dates)edited 2 days ago
answered 2 days ago
Mark Meyer
36.4k32958
36.4k32958
add a comment |
add a comment |
Thanks for contributing an answer to Stack Overflow!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Some of your past answers have not been well-received, and you're in danger of being blocked from answering.
Please pay close attention to the following guidance:
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f54000799%2fis-there-a-better-way-to-extract-information-from-a-string%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
3
Why not use array.map?
– Henry Howeson
2 days ago
@HenryHoweson
.map(alone) won't work if there's more than one date in one of the input strings, eg"1 Ben Howard 12/16/1988 apple 1/10/1999 ", he'd have to flatten it afterwards– CertainPerformance
2 days ago
1
@CertainPerformance With the regex global flag set it would work fine, also the OP doesn't appear to require that.
– Henry Howeson
2 days ago
@HenryHoweson Just using the global flag doesn't allow for (concise) extraction of matches from multiple strings into a single array, I thought? What code are you thinking of?
– CertainPerformance
2 days ago