I'm writing a program for Uni which requires some basic validation.
I have a textbox which allows the user to input their age. I have successfully written a Regex expression which checks if the value entered into the textbox contains numeric values only and is two characters long:
Regex agePattern = new Regex(#"^[0-9]{1,2}\z$"); // Age entered must be numeric characters only (0-9) and may only be two charaters long
if (agePattern.IsMatch(ageBox.Text) == false)
{
MessageBox.Show("Customer's age is not valid. Age must be in numeric format & can only be two characters long"); // If Regex pattern & entered string DO NOT match - user get's this message
return;
}
else
{
// do something
}
My question is, can I extend my Regex expression to constrain age values between 1 and 99?
I've not written any Regex before and I'm struggling.
Thanks!
How about parsing an integer instead?
bool IsValidAge(string ageString) {
int age;
return int.TryParse(ageString, out age) && age >= 1 && age <= 99;
}
Try this regex:
^[1-9]?[0-9]?\z
Or skip regex, parse the text as int and write a function which decide input is between 1 and 99.
Try this regex:
^[1-9]?[0-9]?\z
This matches an empty input (since both digits are optional) as well as 0. Fewer ? are better:
^[1-9][0-9]?$
Try it with A Better .NET Regular Expression Tester (most other online testers don't allow to specify an empty source).
Related
This question already has answers here:
Identify if a string is a number
(26 answers)
Closed 6 years ago.
else if (vReadData.Length==14 && vReadData Is Numeric)
{
if (txtIPLoad_MHEBarcode1.Text == "")
{
txtIPLoad_MISBarcode1.Text = vReadData;
txtIPLoad_MHEBarcode1.Focus();
}
else
{
txtIPLoad_MISBarcode2.Text = vReadData;
txtIPLoad_MHEBarcode2.Focus();
}
mMessage("Scan", "Please scan the MHE Barcode!");
return;
}
This is my code for validating a Textbox. I check the condition that the length should be 14 chars. I must also check that the input which comes in variable vReadData must be numeric (only numbers).
Please help me solve this.
I have tried using
else if (Int64.TryParse(vReadData, out num))
but this is not helping me.
Are you looking for a regular expression?
else if (Regex.IsMatch(vReadData, #"^[0-9]{14}$")) {
// vReadData is a string of exactly 14 digits [0..9]
}
Explanation: we have to match two conditions
The string should be exactly 14 characters long
It should be a valid (non-negative) number (I doubt if any negative bar code exits)
After combining both conditions into one we can say that we're looking for a string which consist of 14 digits [0-9] (please notice, that we want [0-9] not \d, since \d in .Net means any digit, including, say Persian ones)
Tests:
string vReadData = #"B2MX15235687CC";
// vReadData = #"12345678901234";
if (Regex.IsMatch(vReadData, #"^[0-9]{14}$"))
Console.Write("Valid");
else
Console.Write("InValid");
Outcome:
InValid
If you uncomment the line you'll get
Valid
Is there a way to validate 'live' input field using Regex in C#?
'live' means that I don't validate complete string, I want to validate the string while it's typed.
For example, I want my string to match the next pattern lalala111#alalala123, so I have to check each new char - is it # ? if it's # then is there a # already in the string? if yes, then I return a null, if no, then I return the char. And of course I have to check chars - is it letter or digit? if yes, then ok, if not, then not ok.
I hope you got my idea.
At now I have this code
private char ValidateEmail(string input, int charIndex, char charToValidate)
{
if (char.IsLetterOrDigit(charToValidate) &&
!(charToValidate >= 'а' && charToValidate <='я') &&
!(charToValidate >= 'А' && charToValidate <= 'Я') ||
charToValidate =='#' ||
"!#$%&'*+-/=?^_`{|}~#.".Contains(charToValidate.ToString()))
{
if ((charToValidate == '#' && input.Contains("#")) ||
(!input.Contains("#") && charIndex>=63) ||
(input.Contains("#") && charIndex >= 192))
return '\0';
}
else
{
return '\0';
}
return char.ToUpper(charToValidate);
}
it allows only latin letters with digits and some special characters, and also it allows first part of the string (before #) to have only 64 letters, and the second part (after #) to have only 128 letters, but the code looks ugly, don't it? So I want to do all these checks in one beauty regular expression.
lYou have to use the following code:
Declare this line at top:
System.Text.RegularExpressions.Regex remail = new System.Text.RegularExpressions.Regex(#"^([a-zA-Z0-9_\-\.]+)#((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?)$");
next either on button click or leave event pass the following code to check
if (textemail.Text != "" && !remail.IsMatch(textemail.Text))
{
errorProvider1.Clear();
textemail.Focus();
errorProvider1.SetError(textemail, "Wrong Email ID");
MessageBox.Show("Wrong Email ID");
textemail.SelectAll();
return;
}
After a character has been typed, you want the string that has been entered to match one of the following:
between 1 and 64 (inclusive) acceptablecharacters.
between 1 and 64 (inclusive) acceptable characters then an # character.
between 1 and 64 (inclusive) acceptable characters then an # character then 128 or fewer acceptable characters.
Note that the last two clauses can be combined to say:
between 1 and 64 (inclusive) acceptable characters then an # character then between 0 and 128 inclusive acceptable characters.
Hence the entire requirement can be expressed as:
between 1 and 64 (inclusive) acceptable characters, optionally followed by an # character then between 0 and 128 inclusive acceptable characters.
Where the definition of "acceptable characters" is not at all clear from the question. The code within ValidateEmail does range checks of 'a' to 'я' and of 'А' to 'Я'. It also checks "!#$%&'*+-/=?^_{|}~#.".Contains(...)`.
The text below assumes acceptable characters actually means the 26 letters, upper and lower case, plus the 10 digits.
The required regular expression is then ^\w{1,64}(#\w{0,128})?$
This regular expression can then be used to check the concatenation of the already validated input text plus the character just typed.
If additional characters are wanted to be considered as acceptable then change the \w, there are two of them. For example if underscores (_) and hyphens (-) are to be allowed then change both \ws to be [\w_-].
I have had a difficult time wrapping my head around regular expressions. In the following code, I used a Regex to determine if the data passed was a 1 to 3 digit number. The expression worked if the data started with a number (ex. "200"), but also passed if the data had a letter not in the first digit (ex. "3A5"). I managed to handle the error with the INT32.TryParse() method, but it seems there should be an easier way.
if (LSK == MainWindow.LSK6R)
{
int ci;
int length = SP_Command.Length;
if (length > 3) return MainWindow.ENTRY_OUT_OF_RANGE; //Cannot be greater than 999
String pattern = #"[0-9]{1,3}"; //RegEx pattern for 1 to 3 digit number
if (Regex.IsMatch(SP_Command, pattern)) //Does not check for ^A-Z. See below.
{
bool test = Int32.TryParse(SP_Command, out ci); //Trying to parse A-Z. Only if
if (test) //it no letter will it succeed
{
FlightPlan.CostIndex = ci; //Update the flightplan CI
CI.Text = ci.ToString(); //Update the Init page
}
else return MainWindow.FORMAT_ERROR; //It contained a letter
}
else return MainWindow.FORMAT_ERROR; //It didn't fit the RegEx
}
Regex.IsMatch searches the input string for the pattern (and thus returns true for 3A5 because it finds 3).
You should also include start (^) and end ($) of string:
String pattern = #"^[0-9]{1,3}$";
Adding line begin/end should help.
^[0-9]{1,3}$
I'm using the following code to accept user input. I want to limit user input to a single alpha (a-z) character only. I'm finding a lot of validations using IsNumber to validate integer input, and a lot of information about using a regex on an input String, but I've been unable to uncover how I would be able to restrict input possibilities with this code. Can someone point me in the right direction?
public char promptForGuess()
{
Console.Write("\nGuess a letter: ");
String pre = Console.ReadKey().Key.ToString();
string pre2 = pre.ToUpper();
char pre3 = Convert.ToChar(pre2);
}
You cannot limit the user only put in a-z chars on the console - you have to check the input, he can write in any character (just think about when the input is redirected to your program from a file with <, e.g. yourapp.exe < input.dat ).
But its easy to check a character is lowercase a-z letter. E.g. with plain, ASCII, C tactic (I will use your defined variables):
if('A' <= pre3 && pre3 <'Z') { // pre3 was made upper in your code
// input OK
} else {
// input NOK
}
With regex:
Regex r = new Regex(#"^[a-zA-Z]$");
return r.IsMatch(pre);
If you cannot allow case-insensitive characters, just change the code I wrote.
Anyway, I think you need Console.Read() (ReadKey also read keys like arrows, F1-F12 etc..., so ALL keys, even tab and caps lock). Refer to MSDN: http://msdn.microsoft.com/en-us/library/system.console.read.aspx
And maybe you should use this function, if you would support unicode letters: http://msdn.microsoft.com/en-us/library/yyxz6h5w.aspx
Note that unicode letters are usually not one bytes! But char can store it. These letters are for example beautiful Hungarian letters with acutes and these king of things: á, é, ő, ű, ö, ü etc (but also French have a lot, and also Dutch etc...)
For judging a valid string, you could judge by
str.length() == 1 && str[0] >= 'a' && str[1] <= 'z'
and for restricting input possibilities, you could write a loop that loops if the input is invalid.
pre = read();
while (!valid(pre))
pre = read();
why don't you use Regex
if (Regex.IsMatch(pre[0].ToString(), #"[A-Za-z]"))
{
//do someting
}
else
{
//do someting
}
In my C# application, I use a regular expression to validate the basic format of a US phone number to make sure that the user isn't just entering bogus data. Then, I strip out everything except numbers, so this:
(123) 456-7890 x1234
becomes
12345678901234
in the database. In various parts of my application, however, I would like to convert this normalized phone number back to
(123) 456-7890 x1234
What's the best way to do such a thing? (Don't worry about accounting for international phone number formats, by the way.)
String.Format("{0:(###) ###-#### x ###}", double.Parse("1234567890123"))
Will result in (123) 456-7890 x 123
Using a regex you can replace:
(\d{3})(\d{3})(\d{4})(\d{4})
with:
(\1) \2-\3 x\4
(Though I'm not familiar with US phone numbers so maybe there's more to it.)
I would just use a custom format string to transform the number back into the string:
class Program
{
static void Main(string[] args)
{
long phoneNumber = 12345678901234;
string phoneNumberString = String.Format("{0:(000) 000-0000 x0000}", phoneNumber);
Console.WriteLine(phoneNumberString);
}
}
Of course, you would factor it out into a function which would take the phone number as a long and then return the string (with the format loaded or stored as a constant in the method, or something appropriate for your situation).
Oh, and if you have it in a string and not a long, you can easily convert the string to a long, and then pass it to the format function. Of course, there are performance considerations here if you are doing it repeatedly (since you are iterating the string to create the long, and then converting it back to a string, when you could just use substring).
If you only support US numbers, you could simply format the digits to show parenthesis and x wherever you want.
I would prefer to store the whole string, I would parse it using a regex to validate it, then store it in a normalized string.
To make it accept any country, I would do this:
I would add the IDD code to all phone numbers, and then hide it from users from that country.
so: (123) 456-7890 x1234 would be stored as +1 (123) 456-7890 x1234
The (perl-compatible) regex would be something like (completely untested and wouldn't work) :
(+\d+)?\s+(((\d{,3}))(?\s+([-.0-9]{6,})\s+((x|ext\w*)\d{,4})
This is an optional number of digits preceded by +
Followed by one or more spaces
Then an optional group of up to 3 digits between parenthesis
Then one or more spaces
Then a group of 6 or more digits, dashes or dots
Then one or more spaces
Then an optional x or a word that begins with ext (ext, extension ...) and a group of up to 4 digits
I would have a database of users including country and area code, then fill those in automatically in case they're missing, the country would have it's default digit grouping convention for phone numbers (3,4 for the us).
So if you're in area 123 in the us, and enter 456.7890, it would be parsed as +1 (123) 4567890, and you would only see it as 456-7890
if you're in Qatar and enter the number 4444555 extenshn 33, it is stored as +974 4444555 x33, you would see it as 4444555 x33
The international code will not be displayed for users in the same country, and the area code will not be displayed for users in the same country and area code. The full number would be displayed onmouseover (HTML label?)
Do you HAVE to break it down for the DB? If not, don't. If you MUST, then you can either store the different parts in different fields, (Areacode, Prefix, SubscriberNum, Extenion).
Or, extract the number, and begin parsing. If it's only 10 digits, then you know there is no extension. All digits past 10, stick them in the string after an 'x' or something.
I did something similar to this in a C++ app I wrote the stored different contact mechanisms as a single string, but instead, I did the reverse of what you are doing. I took the fields off a dialog, and built the formatted number to store as a string.
Here's an extension method that might help:
public static string InsertStringAtPositions(this string str, string insertStr, IEnumerable<int> positions)
{
if (str != null && insertStr != null && positions != null)
{
string newString = string.Empty;
int previousPos = 0;
foreach (var pos in positions)
{
if (pos < str.Length)
{
newString += str.Substring(previousPos, pos - previousPos) + insertStr;
previousPos = pos;
}
}
if (positions.Last() < str.Length)
{
return newString + str.Substring(positions.Last(), str.Length - positions.Last());
}
return newString;
}
return str;
}
Usage:
// Will convert "0399998888" to "03 9999 8888"
number.InsertStringAtPositions(" ", new[] {2, 6});