textbox validation accepting Ports in javascript - javascript

the question was accepting one or many ports that has one space between them with help of friends,
I used this one for my answer but for example if I enter 88888 it will alert me such this thing:
88888NaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaN is not correct
how can I correct this
<script type="text/javascript">
function portvalidating(field)
{
var output='';
m=field.value;
if(/^\d{1,5}([ ]\d{1,5})*$/.test(m))
{
var parts = m.split(' ');
for(i in parts)
{
var p= parseInt(parts[i]);
if(!((0 <= p) && (p<= 65535) && !isNaN(p)))
{
output+=p;
}
}
if(output=='')
var dummy=1;
else alert(output+'is not correct');
}
else alert('please enter a valid port!');
}

Unfortunately, regular expressions can't handle 'ranges', so you can't do this exactly as you want with regexp (therorically you can, but the regex would be hiper,hiper long).
However, you could validate your space-separated numbers with this regexp:
/^\d{1,5}([ ]\d{1,5})*$/
This will do what you want, except validating the range you supplied. But it controls that numbers have between 1 and 5 digits, and the other things you asked.
Hope this helps. Cheers

A crude regex without much error checking would be: exp = /\d{1,5}/g and then call .match(exp) on your string. However, you will need to use parseInt to convert the output to a number so that you can check it's value against your constraints.
I think you may be able to do this easier without Regex. Some quick code to split and parse a string is:
var s = "21 456 -32 70000";
var parts = s.split(' ');
var output;
for(i in parts)
{
p = parseInt(parts[i]);
if( (0 <= p) && (p <= 65535) && !isNaN(p) )
output += p+"<br />";
}
Hopefully this helps to some degree.

I think you would compromise your performance here if you want you are trying to validate a simple Integer value via RegEx.
IMO, try spiting the string with Space (' ') and and convert each value to Integer and perform myInt < 65535.
for( String str : portNumbers.split(' ') ){
try{
int i = Integer.parseInteger( str );
if( 0 > i && i > 65535 ){
errorMessage = str + " is out of range.";
}
}catch (NumberFormatException e) {
errorMessage = str + " is not a valid port.";
}
}

(6553[0-5]|655[0-2][0-9]|65[0-4][0-9][0-9]|6[0-4][0-9][0-9][0-9]|\d{2,4}|[1-9])

Related

Validating phone number with different formats WITHOUT regex

In JavaScript, I need validate phone numbers without using regular expressions (must be with string manipulation). The phone numbers have to be in one of the following formats:
123-456-7890
1234567890
(123)4567890
(123)456-7890
Then I must also provide an alert if the phone number isn't in one of the formats listed above.
I have only been able to manage to get #2 working, which looks something like this:
function len(gth)
{
if (gth.value.length != 10)
{
alert("Telephone numbers MUST be 10 digits!");
}
}
which down in the HTML it would call up to the function:
<p>Phone: <input id = "phone" onblur="len(this)" name = "Phone" size = "20" type = "text" maxlength = "10"> </p>
Since you need a solution without regex, I believe this should work.
const phones = [
'123-456-7890',
'1234567890',
'(123)4567890',
'(123)456-7890',
'+61(123) 456-7890',
'12345',
'))))01/34$89.77(99'
]
function len(gth) {
if (gth.substring(3, 4) == '-' && gth.substring(7, 8) == '-') // 123-456-7890
gth = gth.replace('-', '').replace('-', '');
else if (gth.substring(0, 1) == '(' && gth.substring(4, 5) == ')' && gth.substring(8, 9) == '-') // (123)456-7890
gth = gth.replace('(', '').replace(')', '').replace('-', '');
else if (gth.substring(0, 1) == '(' && gth.substring(4, 5) == ')') // (123)4567890
gth = gth.replace('(', '').replace(')', '');
if (!isNaN(gth) && gth.length == 10) {
return true;
}
alert("Telephone numbers:" + gth + " MUST be 10 digits!");
}
phones.forEach(len)
I would replace the numbers with something like x, then check against predefined patterns:
function check(num) {
let pattern = '';
for (let i = 0; i < num.length; i++) {
pattern += num[i] >= '0' && num[i] <= '9' ? 'x' : num[i];
}
return ['xxx-xxx-xxxx', 'xxxxxxxxxx', '(xxx)xxxxxxx', '(xxx)xxx-xxxx']
.indexOf(pattern) >= 0;
}
For extra credit, find the bug in the above program.
However, you don't really need to do any of this. You should be able to use the pattern attribute on the input element. That will also provide a better user experience. For instance, you can style the input element using the :invalid pseudo-class, by putting a red border around it for example, to give the user real-time feedback that their input is not valid. Yes, that takes a regular expression--what was your reason for not wanting to use a regular expression again?
You can make it manually be:
Checking string size if it is the expected or not
split the string to char array then parse them as integers inside a try block if numberFormatException is thrown it should be a bracket ( ) or -
Basic example of extracting the input data to Array
function test() {
var phnTest = document.getElementById('phone').value;
var strArray = [];
strArray = phnTest.split('');
document.getElementById('p').innerHTML = strArray;
}
<form action="demo_form.asp">
Phone <input id="phone" type="text" name="phone"><br>
<input type="button" value='Submit' onclick="test()">
</form>
<p id='p'></p>
This is dependent on how the data is structured, if you need to search a body of text and so on, but basics would be...
If it's a simple pull from an <input>, grab the data...
Take the input data, and generate an array with each character. You could then test, say strArray[3], for a dash or a dot. If not present, it can continue along to check for seven numbers in a row and so on.
This is going to be extremely consuming and require a number of conditionals to be checked. I assume the "without RegEx" is a requirement for a project or such, if not, recommend learning and using RegEx.
Hope this gets you going.
This is my attempt. The key is creating an array from the string then filtering out any non numerical characters. It would be easier to use regular expression though. just
number.replace(/(\D+)/g, '')
const numbers = [
'123-456-7890',
'1234567890',
'(123)4567890',
'(123)456-7890',
'+61(123) 456-7890',
'12345',
'))))01/34$89.77(99'
]
// validate a phone number
function validate(number) {
const digits = clean(number)
console.log({
number,
digits,
length: digits.length,
pass: digits.length === 10
})
}
// remove any non digits from the number
function clean(number) {
return Array.from(number).filter(char => {
return !isNaN(char) && char !== ' '
}).join('')
}
numbers.forEach(validate)

Find all instances and display alert - part 2, now with regex

Thanks for your help with my earlier question:
How to find all instances and display in alert
Now I discover that I need to include some invalid character validation.
I'm trying to figure out how to include a set of regex invalid characters as part of the validation that will also show up in the same alert/textbox/whatever as the "too long/too short" validation.
So, I have a textbox which users will type or paste comma separated values such as AAAAAAA,BBBBBBB,CCCCCCCC,DDDDDDDD
And they cannot be more or less than seven characters long and they can only include certain characters.
I currently have have two separate pieces of Javascript that I'm trying to now combine:
var Invalidchars = "1234567890!##$%^&*()+=[]\\\';./{}|\":<>?";
for (var i = 0; i < document.getElementById("TextBox1").value.length; i++) {
if (Invalidchars.indexOf(document.getElementById("TextBox").value.charAt(i)) != -1){
alert
and this
var val = document.getElementById("Textbox1").value,
err = $.grep(val.split(','), function(a) { return a.length != 7; });
if (err.length) {
alert("All entries must be seven (7) characters in length. Please correct the following entries: \n" + err);
return false;
}
return true;
Any help is much appreciated!
=================================================
SOLUTION
Took a while, but using Tenub's code (which didn't quite combine my two sets code, but was close enough), I finally figured out how to merge my two sets of code into one. Here's the code if anyone is ever interested in using it:
var val = document.getElementById("TextBox1").value,
err = $.grep(val.split(','), function(a) {return (a.length = (!/^[^0-9!##$%^&*()+=;.\/\{}|:<>\\?\[\]\'\"]{7}$/.test(a)));});
if (err.length){
document.getElementById("DIV1").style.display = "inline-block";
document.getElementById("TextBox2").value = err.join(',');
return callback (false);
}
document.getElementById("DIV1").style.display = "none";
return true;
The answer is as simple as it is elegant:
var val = document.getElementById("Textbox1").value;
if(!/[^0-9!##$%^&*()+=;./{}|:<>?\[\]\\\'\"]{7}/.test(val)) {
// handle invalid value
}
This tests that the string is 7 characters in length and does not contain any character within the brackets after the "^" (also some characters are escaped with a "\").
You can test in console:
/[^0-9!##$%^&*()+=;./{}|:<>?\[\]\\\'\"]{7}/.test('adfFDKZ'); // returns true
/[^0-9!##$%^&*()+=;./{}|:<>?\[\]\\\'\"]{7}/.test('adf(DKZ'); // returns false
Try this:
/*
* This regex matches all the invalid characters. I escaped the
* special characters.
*/
var regex = /.*[0-9!##\$%\^&\*\(\)\+=\[\]\\';\./\{\}\|":\<\>\?]+.*/;
var text = document.getElementById("TextBox1").value;
/* Test for match...much faster than a for-loop under any circumstances */
if (text.matches(regex)) {
alert("Invalid characters present. Please correct the input");
return false;
}
/* split on delimiter */
var err = $.grep(val.split(','), function(a) { return a.length != 7; });
if (err.length) {
alert("All entries must be seven (7) characters in length. Please correct the following entries: \n" + err);
return false;
}
Please tell me if there are any bugs in this. Also, the only real way to test for this in one step is to set up an enormously long regex. Also, with only one check, it would make it a little harder to guide the user to make the right correction. I will mention that.

Show numbers to second nearest decimal

I'm very new to Javascript so please bear with me.
I have this function that adds up a total. How do I make it so that it shows the nearest two decimal places instead of no decimal places?
function calcProdSubTotal() {
var prodSubTotal = 0;
$(".row-total-input").each(function() {
var valString = $(this).val() || 0;
prodSubTotal += parseInt(valString);
});
$("#product-subtotal").val(CommaFormatted(prodSubTotal));
}
Thank you!
Edit: As requested: commaFormatted:
function CommaFormatted(amount) {
var delimiter = ",";
var i = parseInt(amount);
if(isNaN(i)) { return ''; }
i = Math.abs(i);
var minus = '';
if (i < 0) { minus = '-'; }
var n = new String(i);
var a = [];
while(n.length > 3)
{
var nn = n.substr(n.length-3);
a.unshift(nn);
n = n.substr(0,n.length-3);
}
if (n.length > 0) { a.unshift(n); }
n = a.join(delimiter);
amount = "$" + minus + n;
return amount;
}
Well parseInt parses integers, so you are getting rid of any decimals right there. Use parseFloat.
E.g.
parseFloat('10.599').toFixed(2); //10.60
You might also want to change your commaFormatted function to something like:
function commaFormatted(amount) {
if (!isFinite(amount) || typeof amount !== 'number') return '';
return '$' + amount.toFixed(2).replace(/(\d)(?=(\d{3})+(?!\d))/g, '$1,');
}
commaFormatted(0); //$0.00
commaFormatted(1.59); //$1.59
commaFormatted(999999999.99); //$999,999,999.99
Use to function toFixed(2)
The 2 is an integer parameter that says use 2 decimal points, assuming your comma formatted code does not turn it into a string. (If it does, fix the decimals BEFORE you run it through the formatting)
$("#product-subtotal").val(CommaFormatted(parseFloat(prodSubTotal).toFixed(2)));
Remember to parseFloat because the val() could be a string!`
You're looking for toFixed(). It takes one parameter, digits. The parameter is documented as follows:
The number of digits to appear after the decimal point; this may be a value between 0 and 20, inclusive, and implementations may optionally support a larger range of values. If this argument is omitted, it is treated as 0.
Do also note that parseInt() parses integers, truncating any decimals you might have. parseFloat() will preserve decimals as expected.
I solved my problem. I simply changed:
$("#product-subtotal").val(CommaFormatted(prodSubTotal));
to
$("#product-subtotal").val(prodSubTotal);
As I stated in the comments, this was not a script I wrote. It is a script Chris Coyier wrote and I was just trying to amend it. I guess I didn't need to use CommaFormatted for my purposes?
Thank you all for your help!

Regex expression in javascript to validate number [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Simple regular expression for a decimal with a precision of 2
HI i need to validate a number using regex. The main idea is that i have the integer part, the decimal part and the decimal separator of a number. For example if i have this:
var integer_part = 4;
var decimal_part = 2;
var decimal_separator = ".";
// will be valid numbers
// 2546.33
// 12
// 1.33
// 263
// 0
can i make a regex string with the values in the variables to validate a string ¿?
You don't need a regex for this:
!isNaN(parseFloat(n)) && isFinite(n);
That checks a number is a float, isn't NaN and isn't infinity.
This sounds like an XY problem. What you should have asked is How can I validate a number? and left the regex part out.
Though it is not clear from your question, I am assuming you want to use the variables to determine the range of allowable values in your regex If so, you can make your pattern string like this:
pattern = '/[\d]{0,' + integer_part + '}(' + decimal_separator + '[\d]{1,' + decimal_part + '})?/';
This is a basic implementation. In this case, in order to use . as you separator you would actually want to set decimal_separator = '\.'; This is to escape the decimal which is wildcard match in regex.
If you really want to look for more edge cases, you might want to build up your pattern conditionally like this:
pattern = '/[\d]{0,' + integer_part + '}';
if (decimal_part > 0) {
if (decimal_separator == '.') {
pattern += '(\.';
} else {
pattern += '(' + decimal_separator;
}
pattern += '[\d]';
if (decimal_part == 1) {
pattern += '{1}';
} else {
pattern += '{1,' + decimal_part + '}';
}
pattern += ')?';
}
pattern += '/';
Just use this regex, it will look for anything with
\d+(\.\d+)
However, there might be a better way to do it.
Boolean isFloat=false;
try
{
float num=parseFloat(n);
isFloat=!isNaN(num) && isFinite(num);
}
catch (NumberFormatException ex)
{
//Isn't a number
}

Convert String with Dot or Comma as decimal separator to number in JavaScript

An input element contains numbers a where comma or dot is used as decimal separator and space may be used to group thousands like this:
'1,2'
'110 000,23'
'100 1.23'
How would one convert them to a float number in the browser using JavaScript?
jQuery and jQuery UI are used. Number(string) returns NaN and parseFloat() stops on first space or comma.
Do a replace first:
parseFloat(str.replace(',','.').replace(' ',''))
I realise I'm late to the party, but I wanted a solution for this that properly handled digit grouping as well as different decimal separators for currencies. As none of these fully covered my use case I wrote my own solution which may be useful to others:
function parsePotentiallyGroupedFloat(stringValue) {
stringValue = stringValue.trim();
var result = stringValue.replace(/[^0-9]/g, '');
if (/[,\.]\d{2}$/.test(stringValue)) {
result = result.replace(/(\d{2})$/, '.$1');
}
return parseFloat(result);
}
This should strip out any non-digits and then check whether there was a decimal point (or comma) followed by two digits and insert the decimal point if needed.
It's worth noting that I aimed this specifically for currency and as such it assumes either no decimal places or exactly two. It's pretty hard to be sure about whether the first potential decimal point encountered is a decimal point or a digit grouping character (e.g., 1.542 could be 1542) unless you know the specifics of the current locale, but it should be easy enough to tailor this to your specific use case by changing \d{2}$ to something that will appropriately match what you expect to be after the decimal point.
The perfect solution
accounting.js is a tiny JavaScript library for number, money and currency formatting.
Check this for ref
You could replace all spaces by an empty string, all comas by dots and then parse it.
var str = "110 000,23";
var num = parseFloat(str.replace(/\s/g, "").replace(",", "."));
console.log(num);
I used a regex in the first one to be able to match all spaces, not just the first one.
This is the best solution
http://numeraljs.com/
numeral().unformat('0.02'); = 0.02
What about:
parseFloat(str.replace(' ', '').replace('.', '').replace(',', '.'));
All the other solutions require you to know the format in advance. I needed to detect(!) the format in every case and this is what I end up with.
function detectFloat(source) {
let float = accounting.unformat(source);
let posComma = source.indexOf(',');
if (posComma > -1) {
let posDot = source.indexOf('.');
if (posDot > -1 && posComma > posDot) {
let germanFloat = accounting.unformat(source, ',');
if (Math.abs(germanFloat) > Math.abs(float)) {
float = germanFloat;
}
} else {
// source = source.replace(/,/g, '.');
float = accounting.unformat(source, ',');
}
}
return float;
}
This was tested with the following cases:
const cases = {
"0": 0,
"10.12": 10.12,
"222.20": 222.20,
"-222.20": -222.20,
"+222,20": 222.20,
"-222,20": -222.20,
"-2.222,20": -2222.20,
"-11.111,20": -11111.20,
};
Suggestions welcome.
Here's a self-sufficient JS function that solves this (and other) problems for most European/US locales (primarily between US/German/Swedish number chunking and formatting ... as in the OP). I think it's an improvement on (and inspired by) Slawa's solution, and has no dependencies.
function realParseFloat(s)
{
s = s.replace(/[^\d,.-]/g, ''); // strip everything except numbers, dots, commas and negative sign
if (navigator.language.substring(0, 2) !== "de" && /^-?(?:\d+|\d{1,3}(?:,\d{3})+)(?:\.\d+)?$/.test(s)) // if not in German locale and matches #,###.######
{
s = s.replace(/,/g, ''); // strip out commas
return parseFloat(s); // convert to number
}
else if (/^-?(?:\d+|\d{1,3}(?:\.\d{3})+)(?:,\d+)?$/.test(s)) // either in German locale or not match #,###.###### and now matches #.###,########
{
s = s.replace(/\./g, ''); // strip out dots
s = s.replace(/,/g, '.'); // replace comma with dot
return parseFloat(s);
}
else // try #,###.###### anyway
{
s = s.replace(/,/g, ''); // strip out commas
return parseFloat(s); // convert to number
}
}
Here is my solution that doesn't have any dependencies:
return value
.replace(/[^\d\-.,]/g, "") // Basic sanitization. Allows '-' for negative numbers
.replace(/,/g, ".") // Change all commas to periods
.replace(/\.(?=.*\.)/g, ""); // Remove all periods except the last one
(I left out the conversion to a number - that's probably just a parseFloat call if you don't care about JavaScript's precision problems with floats.)
The code assumes that:
Only commas and periods are used as decimal separators. (I'm not sure if locales exist that use other ones.)
The decimal part of the string does not use any separators.
try this...
var withComma = "23,3";
var withFloat = "23.3";
var compareValue = function(str){
var fixed = parseFloat(str.replace(',','.'))
if(fixed > 0){
console.log(true)
}else{
console.log(false);
}
}
compareValue(withComma);
compareValue(withFloat);
This answer accepts some edge cases that others don't:
Only thousand separator: 1.000.000 => 1000000
Exponentials: 1.000e3 => 1000e3 (1 million)
Run the code snippet to see all the test suite.
const REGEX_UNWANTED_CHARACTERS = /[^\d\-.,]/g
const REGEX_DASHES_EXEPT_BEGINNING = /(?!^)-/g
const REGEX_PERIODS_EXEPT_LAST = /\.(?=.*\.)/g
export function formatNumber(number) {
// Handle exponentials
if ((number.match(/e/g) ?? []).length === 1) {
const numberParts = number.split('e')
return `${formatNumber(numberParts[0])}e${formatNumber(numberParts[1])}`
}
const sanitizedNumber = number
.replace(REGEX_UNWANTED_CHARACTERS, '')
.replace(REGEX_DASHES_EXEPT_BEGINING, '')
// Handle only thousands separator
if (
((sanitizedNumber.match(/,/g) ?? []).length >= 2 && !sanitizedNumber.includes('.')) ||
((sanitizedNumber.match(/\./g) ?? []).length >= 2 && !sanitizedNumber.includes(','))
) {
return sanitizedNumber.replace(/[.,]/g, '')
}
return sanitizedNumber.replace(/,/g, '.').replace(REGEX_PERIODS_EXEPT_LAST, '')
}
function formatNumberToNumber(number) {
return Number(formatNumber(number))
}
const REGEX_UNWANTED_CHARACTERS = /[^\d\-.,]/g
const REGEX_DASHES_EXEPT_BEGINING = /(?!^)-/g
const REGEX_PERIODS_EXEPT_LAST = /\.(?=.*\.)/g
function formatNumber(number) {
if ((number.match(/e/g) ?? []).length === 1) {
const numberParts = number.split('e')
return `${formatNumber(numberParts[0])}e${formatNumber(numberParts[1])}`
}
const sanitizedNumber = number
.replace(REGEX_UNWANTED_CHARACTERS, '')
.replace(REGEX_DASHES_EXEPT_BEGINING, '')
if (
((sanitizedNumber.match(/,/g) ?? []).length >= 2 && !sanitizedNumber.includes('.')) ||
((sanitizedNumber.match(/\./g) ?? []).length >= 2 && !sanitizedNumber.includes(','))
) {
return sanitizedNumber.replace(/[.,]/g, '')
}
return sanitizedNumber.replace(/,/g, '.').replace(REGEX_PERIODS_EXEPT_LAST, '')
}
const testCases = [
'1',
'1.',
'1,',
'1.5',
'1,5',
'1,000.5',
'1.000,5',
'1,000,000.5',
'1.000.000,5',
'1,000,000',
'1.000.000',
'-1',
'-1.',
'-1,',
'-1.5',
'-1,5',
'-1,000.5',
'-1.000,5',
'-1,000,000.5',
'-1.000.000,5',
'-1,000,000',
'-1.000.000',
'1e3',
'1e-3',
'1e',
'-1e',
'1.000e3',
'1,000e-3',
'1.000,5e3',
'1,000.5e-3',
'1.000,5e1.000,5',
'1,000.5e-1,000.5',
'',
'a',
'a1',
'a-1',
'1a',
'-1a',
'1a1',
'1a-1',
'1-',
'-',
'1-1'
]
document.getElementById('tbody').innerHTML = testCases.reduce((total, input) => {
return `${total}<tr><td>${input}</td><td>${formatNumber(input)}</td></tr>`
}, '')
<table>
<thead><tr><th>Input</th><th>Output</th></tr></thead>
<tbody id="tbody"></tbody>
</table>
From number to currency string is easy through Number.prototype.toLocaleString. However the reverse seems to be a common problem. The thousands separator and decimal point may not be obtained in the JS standard.
In this particular question the thousands separator is a white space " " but in many cases it can be a period "." and decimal point can be a comma ",". Such as in 1 000 000,00 or 1.000.000,00. Then this is how i convert it into a proper floating point number.
var price = "1 000.000,99",
value = +price.replace(/(\.|\s)|(\,)/g,(m,p1,p2) => p1 ? "" : ".");
console.log(value);
So the replacer callback takes "1.000.000,00" and converts it into "1000000.00". After that + in the front of the resulting string coerces it into a number.
This function is actually quite handy. For instance if you replace the p1 = "" part with p1 = "," in the callback function, an input of 1.000.000,00 would result 1,000,000.00

Categories

Resources