0

I have a particular string like below

*WTY:   but the light of the dining room suddenly turn off .
%mor:   conj|but det|the n|light prep|of det|the adj|dining n|room adv|suddenly v|turn adv|off .
%snd:   <00:14:74><00:25:53>
%WTY:   {and} rpl but {suddenly} rpl (0.43) {the} * (1.07) {the light (0.78) suddenly turn off and} # (1.24) the light of the dining room suddenly turn off . err_m_s err_m_l ::: |

I want to extract the numbers inside the round brackets () and count the sum of all these numbers. I have tried the following RegEx for extracting the number but it is not returning any result.

str.match(/\((\d+)\)/)
Bilal Hussain
  • 191
  • 5
  • 18

2 Answers2

2

You can try this:

/\((\d*\.?\d*)\)/g

Explanation

const regex = /\((\d*\.?\d*)\)/g;
const str = `*WTY:   but the light of the dining room suddenly turn off .
%mor:   conj|but det|the n|light prep|of det|the adj|dining n|room adv|suddenly v|turn adv|off .
%snd:   <00:14:74><00:25:53>
%WTY:   {and} rpl but {suddenly} rpl (0.43) {the} * (1.07) {the light (0.78) suddenly turn off and} # (1.24) the light of the dining room suddenly turn off . err_m_s err_m_l ::: |`;
let m;

var val=0.0;
while ((m = regex.exec(str)) !== null) {
    if (m.index === regex.lastIndex) {
        regex.lastIndex++;
    }
    //console.log(m[1]);
    val+=parseFloat(m[1]);
}
console.log(val);

To cover your comment in the accepted answer

Just one more thing what if I have to only count the sum of brackets right before or after the :;: (including :;:a, :;:b, :;:a) .

you can apply this regex :

:;:\s*\((\d*\.?\d*)\)|\((\d*\.?\d*)\)\s*:;:

const regex = /:;:\s*\((\d*\.?\d*)\)|\((\d*\.?\d*)\)\s*:;:/g;
const str = `*WTY:   but the light of the dining room suddenly turn off .
%mor:   conj|but det|the n|light prep|of det|the adj|dining n|room adv|suddenly v|turn adv|off .
%snd:   <00:14:74><00:25:53>
%WTY:   {and} rpl but {suddenly} rpl  :;: (0.43) {the} * (1.07) :;: {the light (0.78) suddenly turn off and} # (1.24) the light of the dining room suddenly turn off . err_m_s err_m_l ::: |`;
let m;

var val=0.0;
while ((m = regex.exec(str)) !== null) {
    if (m.index === regex.lastIndex) {
        regex.lastIndex++;
    }
  if(typeof m[1] !== 'undefined')
    val+=parseFloat(m[1]);
  else
     val+=parseFloat(m[2]);
    //val+=parseFloat(m[1]);
}
console.log(val);
Mustofa Rizwan
  • 10,215
  • 2
  • 28
  • 43
2

The main reason you have no results is that you don't account for the dot in the numbers, so you miss all the non-integer numbers. Once you correct that, you'll still only get one result, because you did not specify the global modifier (g) in your regular expression.

You could use this three-step conversion:

const sum = s.match(/\([\d.]+(?=\))/g) // get the numbers
             .map( a => +a.substr(1) ) // remove opening parenthesis and convert to number
             .reduce( (a,b) => a+b );  // total them

Demo:

const s = `*WTY:   but the light of the dining room suddenly turn off .
%mor:   conj|but det|the n|light prep|of det|the adj|dining n|room adv|suddenly v|turn adv|off .
%snd:   <00:14:74><00:25:53>
%WTY:   {and} rpl but {suddenly} rpl (0.43) {the} * (1.07) {the light (0.78) suddenly turn off and} # (1.24) the light of the dining room suddenly turn off . err_m_s err_m_l ::: |`;

const sum = s.match(/\([\d.]+(?=\))/g) // get the numbers
             .map( a => +a.substr(1) ) // remove opening parenthesis and convert to number
             .reduce( (a,b) => a+b );  // total them

console.log(sum.toFixed(2));

NB: the call to .toFixed is optional, but it solves an issue you might get with floating point inaccuracies.

Community
  • 1
  • 1
trincot
  • 317,000
  • 35
  • 244
  • 286
  • Thank you soo much .This worked . Just one more thing what if I have to only count the sum of brackets right before or after the :;: (including :;:a, :;:b, :;:a) . For example see this fiddle https://jsfiddle.net/y49vgwdz/ โ€“ Bilal Hussain Jan 15 '17 at 12:14
  • That really is worth a new question. It also needs more specifications, like whether you are looking for numbers *between* `:;:`, and/or whether one `:;:` has an effect on a value before *and* after it at the same time, what if `:;:` is followed by a `c` or `d` or `รจ`, ... As you see, there is a lot left for interpretation: better have clear specs, and your attempt (important!) in a new question. โ€“ trincot Jan 15 '17 at 13:37