94f928c5cde29a190e2062fc7bb7fbdb

I'm adding commas to user input numbers on the fly. For example, if I enter 1000, on key up of the last 0, the input field switches the display to 1,000.

# Javascript    
<script type="text/javascript">
    function AddCommas(nStr)
    {	
        nStr += '';
        nStr = nStr.replace(/,/g, '');
        
        x = nStr.split('.');	
        x1 = x[0];	
        x2 = x.length > 1 ? '.' + x[1] : '';	
        
        var rgx = /(\d+)(\d{3})/;	
        while (rgx.test(x1)) 
        {		
            x1 = x1.replace(rgx, '$1' + ',' + '$2');	
        }	
        
        return x1 + x2;
    }
    
    function FormatNumber(obj)
    {
        $('#'+obj).val(AddCommas($('#'+obj).val()));
    }
</script>

# HTML
<input name="txtNumber" type="text" id="txtNumber" onkeyup="javascript:FormatNumber('txtNumber');" />

Refactorings

No refactoring yet !

Aacfa176a8d73ca75b90b6375151765a

paul.wilkins.myopenid.com

June 8, 2010, June 08, 2010 01:44, permalink

1 rating. Login to rate!

Let's get functional on this.

function AddCommas(value) {
    var match = /^(\d+)(\d{3}[\.]?.*)$/.exec(value.replace(/,/g, ''));
    if (match) {
        value = AddCommas(match[1], match[2]);
    }
    return value + (arguments[1] > '' ? ',' + arguments[1] : '');
}
F9a9ba6663645458aa8630157ed5e71e

Ants

June 8, 2010, June 08, 2010 03:06, permalink

No rating. Login to rate!

Sort of on tangent, I hope you know that not all countries/locales use commas as thousands separators.

94f928c5cde29a190e2062fc7bb7fbdb

kathy-wu.myopenid.com

June 8, 2010, June 08, 2010 03:19, permalink

No rating. Login to rate!

Hi Paul,

I'm very new to jquery, so I hope you could help me understand the code. Thanks a lot here in advance.

When I'm calling the above function, there are two errors. First, match[1] and match[2] are both undefined. Second, addCommas() doesn't seem to be recognized. I googled it, this is the link that turned up: http://typi.es/post/488806524/jquery-addcommas. Do I need to reference it?

Also, what is arguments[1]?

Thanks again.
Kathy

94f928c5cde29a190e2062fc7bb7fbdb

kathy-wu.myopenid.com

June 8, 2010, June 08, 2010 03:25, permalink

No rating. Login to rate!

RE Ants, I am aware of that. Currently we don't need to worry about localization. But if there is a solution that I can configure the separator based on a culture locale variable, that will be even better.

Aacfa176a8d73ca75b90b6375151765a

paul.wilkins.myopenid.com

June 10, 2010, June 10, 2010 02:59, permalink

No rating. Login to rate!

The addCommas should be AddCommas

Originally I was using addCommas as the function name, and when renaming after posting so that it was the same as your original function, I missed one.

As for the situation with match[1] and match[2], fixing the first issue should have fixed the second.

Now to explain arguments[1]

All functions can have their arguments accessed via the arguments collection. The argument called value that is passed to the AddCommas function can be accessed directly, or via arguments[0]

The AddCommas function uses a second argument to store the part after the comma. I don't want to define the AddCommas function with a second argument, because that implies that the second argument should be used when first calling it. The solution is to pass the extra argument from within, and then to retrieve it using the arguments collection.

Here's how it works for 100, 1000, and 123456789

With 100, no match is found when it looks for a digit followed by 3 other digits. That [\.]?.* part just caters for optional decimal point values.
As no match is found for 100, it is returned without being changed.

With 1000,
1. a match is found for 1 and 000
2. the function is called with 1 and 000
3.   no match is found within just the 1
4.   1,000 is returned back to the function
5. 1,000 returned out

With 123456789
1.  a match is found for 123456 and 789
2.  the function is called with 123456 and 789
3.    a match is found for 123 and 456
4.    the function is called with 123 and 456
7.      no match is found within just the 123
8.      it joins '123' + ',' + '456' and returns 123,456 back to the function
9.    it joins '123,456' + ',' + '789' returns 123,456,789 back to the function
10. 123,456,879 is returned out

function AddCommas(value) {
    var match = /^(\d+)(\d{3}[\.]?.*)$/.exec(value.replace(/,/g, ''));
    if (match) {
        value = AddCommas(match[1], match[2]);
    }
    return value + (arguments[1] > '' ? ',' + arguments[1] : '');
}
7a0ff0bac0322b11f22aedc85ae618ca

Kelly Taylor

June 18, 2010, June 18, 2010 15:32, permalink

1 rating. Login to rate!

Avoid tail recursion and repeatedly creating the regular expression.

function AddCommas(value) {
    var formatted = String(value).replace(/,/g, '');
    var regex = /^(\d+)(\d{3}[\.]?.*)$/;
    while (regex.exec(formatted)) {
        formatted = RegExp.$1
                ? RegExp.$1 + ',' + RegExp.$2
                : RegExp.$2;
    }
    return formatted;
}
240d80f6a7b8b90fe8a4bb9dbfbcccdf

Brian L

May 13, 2011, May 13, 2011 19:54, permalink

No rating. Login to rate!

How would i use this fvcalc and add the commas into the display at the end?
Thanks

// calculate future value
	function calcFV(){
	//get the values needed for the calculation
	var pv = parseInt(document.getElementById('pvamount').value);
	var yr = parseInt(document.getElementById('timeyears').value);
	var rt = parseFloat(document.getElementById('returnrate').value) / 100;
	
	// making the calculation and displaying the results
	var fv = pv * Math.pow((1 + rt),yr);
	var fvdisplay = "$" + fv.toFixed(0);
	document.getElementById('fvdisplay').innerHTML = fvdisplay;
	return false;
	
	}
	
	
	// display time in years
	function yearsDisplay(){
		var timeyears = document.getElementById('timeyears').value;
		document.getElementById('yearsdisplay').innerHTML = timeyears;
	}
	// display rate of return
	function rateDisplay(){
		var ratevalue = document.getElementById('returnrate').value;
		var returnrate = parseFlost(returnvalue).toFixed(1);
		document.getElementById('ratedisplay').innerHTML = returnrate;
	}


HTML


<h1> Future Valuse Calculator</h1>
<form method="post" action="#" onsubmit="return calcFV()">
	<fieldset>
	<label for="pvamount"> Initial Investment</label>
	<input type="text" id="pvamount" name="pvamount">
	
	<label for="timeyears"> Time Horizon (years) =
		<span id="yearsdisplay">1</span></label>
	<input type="range" value="0" min="1" max="40"
		step="1" id="timeyears" name="timeyears"
		onchange="yearsDisplay()" >
		
	<label for="returnrate"> Rate of Return =
		<span id="ratedisplay">6.0</span>%</label>
	<input type="range" value="6.0" min="6.0" max="15.0"
		step="0.5" id="returnrate" name="returnrate"
		onchange="rateDisplay()" >
		
	<input type="submit" value="Caluculate future value">
	</fieldset>
</form>

<p id="fvdisplay"></p>

Your refactoring





Format Copy from initial code

or Cancel