espresso_coffee
espresso_coffee

Reputation: 6110

How to find time stamp in the string and then convert to number of hours/minutes?

In the column where the hours/minutes are stored for some of the business facilities time stamp(s) are presented in this format 0000-0000. The first two digits represent hours and the other two minutes. Here is example of some business hours:

0700-2300 M-F 0700-1700 S&S
0600-2200
0600-2300 Mon-Fri 0700-2200 Sat&Sun
Local 1 0000-2359 Local 2 0630-2230
0700-2100
0600-2345

The original solution that I had was to convert the values in JavaScript and that it was pretty simple. The problem I have is when there is more than one set of time hours/minutes in the string. In the example above that is the case where hours/minutes are different during the weekend or for the different locations. The JS code example is here:

var time = calcDifference("0600-2345");
function calcDifference(time) {
    var arr = time.split('-').map(function(str) {

        var hours   = parseInt(str.substr(0, 2), 10),
            minutes = parseInt(str.substr(2, 4), 10);
        var result = (hours * 60 + minutes) / 60;
        return result.toFixed(2);
    });
    return arr[1] - arr[0];
}
console.log(time);
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

The code above works just fine if I pass the argument with one time stamp. I'm wondering how to handle situation where I have two time stamps? What would be a good solution to search if string has more than one hours/minutes values and then convert each of them and return to the user.

Upvotes: 1

Views: 105

Answers (3)

ggorlen
ggorlen

Reputation: 56975

You can use a regex like /\d{4}\-\d{4}/g to extract all of the digits from the string and map them to their time differences or replace text in the original.

const calcDifference = range => {
  const time = range.split`-`
    .map(e => (+e.substr(0, 2) * 60 + (+e.substr(2))) / 60)
  return time[1] - time[0];
};

const diffs = `0700-2300 M-F 0700-1700 S&S
0600-2200
0600-2300 Mon-Fri 0700-2200 Sat&Sun
Local 1 0000-2359 Local 2 0630-2230
0700-2100
0600-2345`.replace(/\d{4}\-\d{4}/g, calcDifference);

console.log(diffs);

Upvotes: 1

mrReiha
mrReiha

Reputation: 955

There are plenty of ways to do this ( based on your point of view ), but this is my favourite one. you can manipulate the text then pass numbers individually.

var date = '0700-2300 M-F 0700-1700 S&S'.match( /[-\d]+/gi ).filter( e => ~e.search( /\d+/gi ) )

now you have an array of multiple timestamps saved on your database and you pass them individually to your function.

date.forEach( each => calcDifference( each ) );

Upvotes: 1

Daniel Beck
Daniel Beck

Reputation: 21485

Assuming the HHMM-HHMM format is consistent in the input, and you don't care about discarding the remaining information in the string, regex is probably the simplest approach (and much safer than your current approach of splitting on hyphens, which might easily occur in other parts of the string you don't care about.)

Note that you won't be able to distinguish between "weekend" and "weekday" times, because that information isn't in a consistent format in your input. (This looks like human input, which pretty much guarantees that your HHMM-HHMM format also won't be strictly consistent; consider allowing for optional whitespace around the hyphen for example, and logging strings which show no match so you can check them manually.)

var testinputs = [
  "0700-2300 M-F 0700-1700 S&S",
  "0600-2200",
  "0600-2300 Mon-Fri 0700-2200 Sat&Sun",
  "Local 1 0000-2359 Local 2 0630-2230",
  "0700-2100",
  "0600-2345"
]

var reg = /(\d\d)(\d\d)\-(\d\d)(\d\d)/g; // \d means any digit 0-9; \- matches a literal "-", parens capture the group for easier access later

for (input of testinputs) {
  console.log("Input: ", input)
  var matches;
  while ((matches = reg.exec(input)) !== null) { // loop through every matching instance in the string
    // matches[0] is the full HHMM-HHMM string; the remainder is 
    // the HH and MM for each parenthetical in the regexp:
    console.log(matches) 
  }
}

Upvotes: 1

Related Questions