5
$\begingroup$

I've been looking for a way to read numbers that have thousands separators in them:

StringCases[" 1142.123 ",  Whitespace ~~ NumberString ~~ Whitespace, 1]

gives

{" 1142.123 "}

but

StringCases[" 1,142.123 ", Whitespace ~~ NumberString ~~ Whitespace, 1]

gives

{}

So ideally there's a Mathematica way of defining NumberString to recognize commas in numbers. Or should I be looking into regexen at this point?

$\endgroup$
6
$\begingroup$

This is admittedly a bit of a hack, but you could remove the commas first, using StringReplace:

StringCases[
 StringReplace[" 1,142.123 ", "," -> ""], 
 Whitespace ~~ NumberString ~~ Whitespace, 1]

(* ==> {" 1142.123 "} *)
$\endgroup$
  • $\begingroup$ This was the solution I used for another question, and as of yet, I don't see a way around it. $\endgroup$ – rcollyer May 3 '12 at 14:02
13
$\begingroup$

I would just go to RegExp:

StringCases[" 1,142.123 ", RegularExpression["\\s[0-9,.]+\\s"], 1]

(* {" 1,142.123 "} *)

You could also go with:

ImportString[" 1,142.123 ","List"]

Though that will automatically change it to Numeric, which doesn't seem to be what you want...

$\endgroup$
  • 1
    $\begingroup$ +1 For anyone who understands regular expressions... $\endgroup$ – Eli Lansey May 3 '12 at 14:15
  • $\begingroup$ I think you meant ImportString, so I fixed it. I had forgotten about that function, +1. $\endgroup$ – rcollyer May 3 '12 at 14:17
  • $\begingroup$ ImportString does many tricks, but sometimes is too slow. Anyway it's a very good option if you don't want to build your own transformation. $\endgroup$ – FJRA May 3 '12 at 14:18
  • $\begingroup$ @rcollyer oops, thanks. My MMA crashed for some reason, so I just typed from memory, but apparently had bad short-term memory $\endgroup$ – tkott May 3 '12 at 14:19
  • $\begingroup$ @EliLansey this made everything crystal clear: regular-expressions.info (sort-of) :) $\endgroup$ – tkott May 3 '12 at 14:20
4
$\begingroup$

Regular expressions are nice, but there is no need to use them here.

numString = (NumberString | ",") .. ;

StringCases[" 1,142.123 ", Whitespace ~~ numString ~~ Whitespace, 1]
{" 1,142.123 "}

The form above is admittedly not robust as a valid number string should not start or end with a comma or have two decimal points, and I believe the comma should not immediately precede a decimal point or appear to its right side. The easiest way I can think to preclude these is to check for them explicitly:

numString = x : (NumberString | ",") .. /;
   ! StringMatchQ[x, ",*" | "*," | "*.*,*" | "*,.*" | "*.*.*"];

StringCases[" 1,2. ,3 4, 5.6,7,.89 0.1.2sam, i am ", numString]
{"1,2.", "3", "4", "5.6", "7", ".89", "0.1", ".2"}
$\endgroup$
  • $\begingroup$ @R.M maybe I need to lern me my's RegEx, but I believe tkott's pattern is equivalent (besides whitespace) to my first form: (NumberString | ",") .. in which case I would argue that, in the context of Mathematica, his is clunky. (Incidentally I already voted for his answer.) $\endgroup$ – Mr.Wizard Aug 18 '12 at 14:45
  • $\begingroup$ I don't know regex well either :P I would've written something like this had I seen this question then too. I assumed his regex was equivalent to the second half of your answer, but on looking closer, I see that's not the case. Including all the exceptions would make his just as clunky, so comment revoked! :) $\endgroup$ – rm -rf Aug 18 '12 at 16:03

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.