Suppressing a trailing "." in numerical output from Mathematica - wolfram-mathematica

Is there some straightforward way to ensure that, when converted to strings, approximate numbers (i.e., numbers with the Real head) won't have a trailing "."? I would like it if they were to only have the decimal point in cases where there's actually a displayed fractional part.
The solutions I've found are not robust, and depend on using Precision and Accuracy together NumberForm in an awkward way, or using RealDigits in an even more awkward way.
Thanks in advance.

I've used this in the past when displaying numbers in figures:
Integerise[x_] := If[Round[x] == x, ToString[Round#x] <> ".0", ToString#x]
Just remove <> ".0" if you don't want integers to be displayed with a zero decimal.
Update: As mentioned by dreeves in the comment, ToString will still truncate a number within 0.0001 or so of an integer and display the dot.
A better way to remove the trailing dot is to use the Inputform format for ToString:
NormalNumber[x_] := ToString[x, InputForm]
with a test:
NormalNumber /# {5, 5.5, 123.001, 123.0001}
This could be incorporated into Integerise above to fix the problem noted.

I recommend this:
shownum[x_] := StringReplace[ToString#NumberForm[x, ExponentFunction->(Null&)],
RegularExpression["\\.$"]->""]
It just does a regex search&replace on the trailing ".". If you want "123." to display as "123.0" instead of "123" then just replace that final empty string with ".0".
UPDATE: My original version displayed wrong for numbers that Mathematica by default displays in scientific notation.
I fixed that with NumberForm.
Here's the version I actually use in real life. It allows for optional rounding:
(* Show Number. Convert to string w/ no trailing dot. Round to the nearest r. *)
Unprotect[Round]; Round[x_,0] := x; Protect[Round];
re = RegularExpression;
shn[x_, r_:0] := StringReplace[
ToString#NumberForm[Round[N#x,r], ExponentFunction->(Null&)], re#"\\.$"->""]

I'd probably just post-process the string. It's faster (and way easier) to just check if the last character is "." than to do redundant arithmetic and take into account all the precision settings.
Edit: maybe you know this, but you can do something like this:
userToString[expr_, form___] := ToString[expr,form];
userToString[expr_Real, form___] := removeTrailingDot[ToString[expr,form]];

The functions NumberForm, ScientificForm, EngineeringForm, etc. ... offers the option NumberFormat to format and arrange the mantissa, base and exponent of a number. With
numberTrim[expr_] := NumberForm[expr,
NumberFormat -> (Row[{StringTrim[#1, "."],
If[#3 == "", "", "\[ThinSpace]\[Times]\[ThinSpace]" <> #2^#3]}] &)];
the default Mathematica output is reproduced, but the trailing dot is removed.

Related

Ruby. Split string in separate decimal numbers

I have a long string which contains only decimal numbers with two signs after comma
str = "123,457568,22321,5484123,77"
The numbers in string only decimals with two signs after comma. How I can separate them in different numbers like that
arr = ["123,45" , "7568,22" , "321,54" , "84123,77"]
You could try a regex split here:
str = "123,457568,22321,5484123,77"
nums = str.split(/(?<=,\d{2})/)
print nums
This prints:
123,45
7568,22
321,54
84123,77
The logic above says to split at every point where a comma followed by two digits precedes.
Scan String for Commas Followed by Two Digits
This is a case where you really need to know your data. If you always have floats with two decimal places, and commas are decimals in your locale, then you can use String#scan as follows:
str.scan /\d+,\d{2}/
#=> ["123,45", "7568,22", "321,54", "84123,77"]
Since your input data isn't consistent (which can be assumed by the lack of a reliable separator between items), you may not be able to guarantee that each item has a fractional component at all, or that the component has exactly two digits. If that's the case, you'll need to find a common pattern that is reliable for your given inputs or make changes to the way you assign data from your data source into str.

Variable floating-point precision format string

I'm trying to print floating point numbers as percentages, and I'd like for the number of digits after the decimal place to vary as needed. Currently I have:
fmt.Printf("%.2f%%\n", 100*(value/total))
The problem is that if my percentage is, say, exactly 50, I will get the following output:
50.00%
While what I want is to get:
50%
Is there any way for the format string to indicate that a maximum of 2 digits of precision should be used, but only if needed?
There's no direct solution with the fmt package.
But you can remove the dot and zeros at end with a regular expression:
r, _ := regexp.Compile(`\.?0*$`)
fmt.Printf("%s%%\n", r.ReplaceAllString(fmt.Sprintf("%.2f", 100*(value/total)),""))
Bonus: the same regex works for any number of trailing zeros.
Side note: You'll display 50.0041 the same way than 50, which might be a little misleading.
There's no way to do that inside fmt with e.g. another flag or what have you. You'll have to write out the logic yourself. You could do something like:
var final string
doubledecimal := fmt.Sprintf("%.2f", 100*value/total)
if doubledecimal[len(doubledecimal)-2:] == "00" {
final = doubledecimal[:len(doubledecimal)-3]
} else {
final = doubledecimal
}
fmt.Printf("%s%%\n, final)
You could similarly use strings.Split to split on the decimal point and work from there.
You could even adjust this to turn 50.10% into 50.1%.
doubledecimal := fmt.Sprintf("%.2f", 100*value/total)
// Strip trailing zeroes
for doubledecimal[len(doubledecimal)-1] == 0 {
doubledecimal = doubledecimal[:len(doubledecimal)-1]
}
// Strip the decimal point if it's trailing.
if doubledecimal[len(doubledecimal)-1] == "." {
doubledecimal = doubledecimal[:len(doubledecimal)-1]
}
fmt.Printf("%s%%\n", doubledecimal)
One way could be to have an if statement controlling the print output, i.e. if the result is cleanly divisible by 1 (result%1 == 0) then print the result to no decimal places. Otherwise print to .2f as you've done above. Not sure if there is a shorter way of doing this, but I think this should work.

Automatically increment filename VideoWriter MATLAB

I have MATLAB set to record three webcams at the same time. I want to capture and save each feed to a file and automatically increment it the file name, it will be replaced by experiment_0001.avi, followed by experiment_0002.avi, etc.
My code looks like this at the moment
set(vid1,'LoggingMode','disk');
set(vid2,'LoggingMode','disk');
avi1 = VideoWriter('X:\ABC\Data Collection\Presentations\Correct\ExperimentA_002.AVI');
avi2 = VideoWriter('X:\ABC\Data Collection\Presentations\Correct\ExperimentB_002.AVI');
set(vid1,'DiskLogger',avi1);
set(vid2,'DiskLogger',avi2);
and I am incrementing the 002 each time.
Any thoughts on how to implement this efficiently?
Thanks.
dont forget matlab has some roots to C programming language. That means things like sprintf will work
so since you are printing out an integer value zero padded to 3 spaces you would need something like this sprintf('%03d',n) then % means there is a value to print that isn't text. 0 means zero pad on the left, 3 means pad to 3 digits, d means the number itself is an integer
just use sprintf in place of a string. the s means String print formatted. so it will output a string. here is an idea of what you might do
set(vid1,'LoggingMode','disk');
set(vid2,'LoggingMode','disk');
for (n=1:2:max_num_captures)
avi1 = VideoWriter(sprintf('X:\ABC\Data Collection\Presentations\Correct\ExperimentA_%03d.AVI',n));
avi2 = VideoWriter(sprintf('X:\ABC\Data Collection\Presentations\Correct\ExperimentB_002.AVI',n));
set(vid1,'DiskLogger',avi1);
set(vid2,'DiskLogger',avi2);
end

Force Ruby to not output a float in standard form / scientific notation / exponential notation

I have the same problem as is found here for python, but for ruby.
I need to output a small number like this: 0.00001, not 1e-5.
For more information about my particular problem, I am outputting to a file using f.write("My number: " + small_number.to_s + "\n")
For my problem, accuracy isn't that big of an issue, so just doing an if statement to check if small_number < 1e-5 and then printing 0 is okay, it just doesn't seem as elegant as it should be.
So what is the more general way to do this?
f.printf "My number: %.5f\n", small_number
You can replace .5 (5 digits to the right of the decimal) with any particular formatting size you like, e.g., %8.3f would be total of 8 digits with three to the right of the decimal, much like C/C++ printf formatting strings.
If you always want 5 decimal places, you could use:
"%.5f" % small_number
I would do something like this so you can strip off trailing zero's:
puts ("%.15f" % small_number).sub(/0*$/,"")
Don't go too far past 15, or you will suffer from the imprecision of floating point numbers.
puts ("%.25f" % 0.01).sub(/0*$/,"")
0.0100000000000000002081668
This works also on integers, trim excess zeros, and always returns numbers as a valid floating point number. For clarity, this uses the sprintf instead of the more cryptic % operator.
def format_float(number)
sprintf('%.15f', number).sub(/0+$/, '').sub(/\.$/, '.0')
end
Examples:
format_float(1) => "1.0"
format_float(0.00000001) => "0.00000001"

RegExp Counting System

I'm trying to create a system where I can convert RegEx values to integers and vice versa. where zero would be the most basic regex ( probably "/./" ), and any subsequent numbers would be more complex regex's
My best approach so far was to stick all the possible values that could be contained within a regex into an array:
values = [ "!", ".", "\/", "[", "]", "(", ")", "a", "b", "-", "0", "9", .... ]
and then to take from that array as follows:
def get( integer )
if( integer.zero? )
return '';
end
integer = integer - 1;
if( integer < values.length )
return values[integer]
end
get(( integer / values.length ).floor) + get( integer % values.length);
end
sample_regex = /#{get( 100 )}/;
The biggest problem with this approach is that a invalid RegExp can easily be generated.
Is there an already established algorithm to achieve what I'm trying? if not, any suggestions?
Thanx
Steve
Since regular expressions can be formally defined by recursively applying a finite number of elements, this can be done: instead of simply concatenating elements, combine them according to the rules of regular expressions. Because the regular language is also recursively enumerable, this is guaranteed to work.
However, it's quite probably overkill to implement this. What do you need this for? Would a simple dictionary of Number -> RegExp key-value pairs not be better suited to associate regular expressions with unique numbers?
I would say that // is the simplest regex (it matches anything). /./ is fairly complex since it is just shorthand for /[^\n]/, which itself is just shorthand for a much longer expression (what that expression is depends on your character set). The next simplest expression would be /a/ where a is the first character in your character set. That last statement brings up an interesting problem for your enumeration: what character set will you use? Any enumeration will be tied to a given character set. Assuming you start with // as 0, /\x{00}/ (match the nul character) as 1, /\x{01}/ as 2, etc. Then you would start to get into interesting regexes (ones that match more than one string) around 129 if you used the ASCII set, but it would take up to 1114112 for UNICODE 5.0.
All in all, I would say a better solution is treat the number as a sequence of bytes, map those bytes into whatever character set you are using, use a regex compiler to determine if that number is a valid regex, and discard numbers that are not valid.

Resources