Regex Usage, or use Substring?

J

jp2msft

Two part question:

1. Is Regex more efficient than manually comparing values using Substring?

2. I've never created a Regex expression. How would I use regex to do the
equivalent of what I have coded using Substrings below?
Code:
string s = TextBox1.Text.ToUpper();
string ch = s.Substring(0, 1); // read first character [B,C,X]
if ((ch == "B") || (ch == "C") || (ch == "X")) {
ch = s.Substring(1, 1); // read second character [P,0,5,7]
if ((ch == "P") || (ch == "0") || (ch == "5") || (ch == "7")) {
if (12 < len) {
ch = " "; // check for spaces in 2 places
if ((s.Substring(7, 1) == ch) && (s.Substring(12, 1) == ch)) {
if (len == 15) {
ok = IsNumeric(new string[] { s.Substring(2, 5), s.Substring(8,
4), s.Substring(13, 2) });
} else {
Console.WriteLine("Non-numeric data found in numeric section.");
}
}
} else {
Console.WriteLine("There should be blanks at positions 8 and 13.");
ok = false;
}
}
} else {
Console.WriteLine("Second letter should be [P, 0, 5, or 7].");
ok = false;
}
} else {
Console.WriteLine("First letter should be [B, C, or X].");
ok = false;
}

Thanks in advance for your help and your time.
 
J

Jon Skeet [C# MVP]

jp2msft said:
Two part question:

1. Is Regex more efficient than manually comparing values using Substring?
Sometimes.

2. I've never created a Regex expression. How would I use regex to do the
equivalent of what I have coded using Substrings below?

Well, let's start off by getting rid of the unnecessary substrings,
when you're only looking at a single character:

string s = TextBox1.Text.ToUpper();
char ch = s[0]; // read first character [B,C,X]
ok = false; // Only one path can produce ok = true
if (ch=='B' || ch=='C' || ch=='X')
{
ch = s[1]; // read second character [P,0,5,7]
if (ch == 'P' || ch == '0' || ch == '5' || ch == '7'))
{
if (len > 12) // Reversed if (12 < len) for readability
{
if (s[7] == ' ' && s[12] == ' ')
{
if (len == 15)
{
ok = IsNumeric(new string[] { s.Substring(2, 5),
s.Substring(8, 4),
s.Substring(13, 2) });
}
else
{
// This message looks incorrect - we've just checked
// the length, not the data
Console.WriteLine
("Non-numeric data found in numeric section");
}
}
else
{
Console.WriteLine
("There should be blanks at positions 8 and 13.");
}
}
}
else
{
Console.WriteLine("Second letter should be [P, 0, 5, or 7].");
}
}
else
{
Console.WriteLine("First letter should be [B, C, or X].");
}

Okay, now assuming that the IsNumeric call is actually to check whether
all of those characters are digits, we could indeed convert all of this
into a regular expression - but it would either match or not. It
wouldn't say which part failed. The regex would be something like:

@"^[BCH][P057]\d\d\d\d\d \d\d\d\d \d\d$"

I haven't tested it, but it looks okay to inspection...
 
A

Arne Vajhøj

jp2msft said:
Two part question:

1. Is Regex more efficient than manually comparing values using Substring?

Only if you write the manual comparing code poorly.
2. I've never created a Regex expression. How would I use regex to do the
equivalent of what I have coded using Substrings below?
Code:
string s = TextBox1.Text.ToUpper();
string ch = s.Substring(0, 1); // read first character [B,C,X]
if ((ch == "B") || (ch == "C") || (ch == "X")) {
ch = s.Substring(1, 1); // read second character [P,0,5,7]
if ((ch == "P") || (ch == "0") || (ch == "5") || (ch == "7")) {
if (12 < len) {
ch = " "; // check for spaces in 2 places
if ((s.Substring(7, 1) == ch) && (s.Substring(12, 1) == ch)) {
if (len == 15) {
ok = IsNumeric(new string[] { s.Substring(2, 5), s.Substring(8,
4), s.Substring(13, 2) });
} else {
Console.WriteLine("Non-numeric data found in numeric section.");
}
}
} else {
Console.WriteLine("There should be blanks at positions 8 and 13.");
ok = false;
}
}
} else {
Console.WriteLine("Second letter should be [P, 0, 5, or 7].");
ok = false;
}
} else {
Console.WriteLine("First letter should be [B, C, or X].");
ok = false;
}

This is a good example of something that should be done as regex,
because the regex will be much easier to read and maintain.

"[BCX][P057]\d{5} \d{4} \d{2}"

should work.

Arne
 
M

Mythran

Jon Skeet said:
jp2msft said:
Two part question:

1. Is Regex more efficient than manually comparing values using
Substring?
Sometimes.

2. I've never created a Regex expression. How would I use regex to do the
equivalent of what I have coded using Substrings below?

Well, let's start off by getting rid of the unnecessary substrings,
when you're only looking at a single character:

string s = TextBox1.Text.ToUpper();
char ch = s[0]; // read first character [B,C,X]
ok = false; // Only one path can produce ok = true
if (ch=='B' || ch=='C' || ch=='X')
{
ch = s[1]; // read second character [P,0,5,7]
if (ch == 'P' || ch == '0' || ch == '5' || ch == '7'))
{
if (len > 12) // Reversed if (12 < len) for readability
{
if (s[7] == ' ' && s[12] == ' ')
{
if (len == 15)
{
ok = IsNumeric(new string[] { s.Substring(2, 5),
s.Substring(8, 4),
s.Substring(13, 2) });
}
else
{
// This message looks incorrect - we've just checked
// the length, not the data
Console.WriteLine
("Non-numeric data found in numeric section");
}
}
else
{
Console.WriteLine
("There should be blanks at positions 8 and 13.");
}
}
}
else
{
Console.WriteLine("Second letter should be [P, 0, 5, or 7].");
}
}
else
{
Console.WriteLine("First letter should be [B, C, or X].");
}

Okay, now assuming that the IsNumeric call is actually to check whether
all of those characters are digits, we could indeed convert all of this
into a regular expression - but it would either match or not. It
wouldn't say which part failed. The regex would be something like:

@"^[BCH][P057]\d\d\d\d\d \d\d\d\d \d\d$"

I haven't tested it, but it looks okay to inspection...

Jon, I believe the first character should be B, C, or X, not H... other
than that, looks ok to me :)

Mythran
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top