简体   繁体   中英

Regex to restrict input into latitude (in decimal degrees) textbox

I have a WPF application with a textbox where my user will enter a latitude value in decimal degrees (with up to 7 digits of precision). Valid latitudes range from -90.0000000 to 90.0000000, of course. I'm trying to create a regex to restrict input via the PreviewTextInput event for the textbox similar to this:

    private void latitudeTextBox_PreviewTextInput(object sender, TextCompositionEventArgs e)
    {
        e.Handled = !ValidateDecimalString(e.Text);
    }

    public static bool ValidateDecimalString(string decimalString)
    {
        Regex regex = new Regex("[^0-9]+");
        return !regex.IsMatch(decimalString);
    }

My current regex allows only numbers to be entered but there are some other limitations that I need to enforce as well like:

  • the latitude could be negative so I need to allow for the minus sign ("-") but only if it appears as the first character
  • the latitude can only contain a single decimal point (".")

Examples of valid latitude values:

  • 90
  • 90.0
  • -90.0000000

Can I achieve these additional restrictions just by modifying my regex? If so, how? Thanks!

try something like this

public static bool ValidateDecimalString(string decimalString)
{
    Regex regex = new Regex(@"^(-)?([0-9]+)(\.[0-9]+)?$");
    return regex.IsMatch(decimalString);
}

for validate range better use converted value like

public static bool ValidateLatitudeString(string decimalString)
{
    if(ValidateDecimalString(decimalString)){
        double lat = 0;
        return double.TryParse(decimalString, out lat) && lat<=90.0 && lat>=-90;
    }
    return false;
}

so possibly better will be without regex like

public static bool ValidateLatitudeString(string decimalString)
{
    double lat = 0;
    return double.TryParse(decimalString, out lat) && lat<=90.0 && lat>=-90;
}

How about this?

public static bool ValidateDecimalString(string decimalString)
{
    Regex regex = new Regex("^-?([0-9]|[1-8][0-9]|90)([.][0-9]*)?$");
    return regex.IsMatch(decimalString);
}

This will allow an optional leading hyphen-minus, followed by a number from 0 to 90 inclusive (but not 999 or 01), followed by optionally a decimal component. It will allow 90.1 though; to forbid this use:

public static bool ValidateDecimalString(string decimalString)
{
    Regex regex = new Regex("^-?(([0-9]|[1-8][0-9])([.][0-9]*)?|90([.]0*))$");
    return regex.IsMatch(decimalString);
}

This will allow 90.0 but not 90.1 .

Lots of options for this. One way -

 #  @"^-?(?:(?:[0-9]|[1-8][0-9])(?:\.[0-9]{1,7})?|90(?:\.0{1,7})?)$"

 ^ 
 -?
 (?:
      (?:
           [0-9] 
        |  [1-8] [0-9] 
      )
      (?: \. [0-9]{1,7} )?
   |  
      90  
      (?: \. 0{1,7} )?
 )
 $

Matching giant edge case

 #  @"^-?(?:(?:[0-9]|[1-8](?:[0-9]|$))(?:\.(?:[0-9]{1,7}|$))?|9(?:0|$)(?:\.(?:0{1,7}|$))?)?$"

 ^ 
 -?
 (?:
      (?:
           [0-9]  
        |  [1-8] (?: [0-9] | $ )
      )
      (?:
           \. (?: [0-9]{1,7} | $ )
      )?
   |  
      9 (?: 0 | $ )
      (?:
           \. (?: 0{1,7} | $ )
      )?
 )?
 $

While your question is how do I validate latitude with regex it seems like a better approach would be to use something like Decimal.TryParse.

 public static bool ValidateLatitudeString(string decimalString)
    {
        decimal validLatitude;
        if (decimal.TryParse(decimalString, out validLatitude))
        {
            if (validLatitude >= -90.0M && validLatitude <= 90.0M)
            {
                return true;
            }
        }

        return false;
    }

另一种方式^-?[0-8]?\\d(?:\\.\\d*)?|-?90(?:\\.0+)?$演示

another way (example with double) - not regex solution but works

        bool IsDigitsOnlyLatitudaLongituda(string str, int deg)
        {
    // deg with value 0 is latitude, deg with value 1 is longitude
            bool provjera = true;
            int brojactocki = 0;
            if (str.Length > 0)
            {
                if (str[0] == '.')
                {
                    provjera = false;
                }
                if (str[str.Length - 1] == '.')
                {
                    provjera = false;
                }
            }
            var brojac = 0;
            foreach (char c in str)
            {
                brojac = brojac + 1;
                if (brojac != 1)
                {
                    if (c == '-')
                    {
                        provjera = false;
                    }
                }
                if (c == '.')
                {
                    brojactocki = brojactocki + 1;
                }
            }
            if (brojactocki > 1)
            {
                provjera = false;
            }
            foreach (char c in str)
            {
                if ((c < '0' || c > '9') && (c != '.') && (c != '-'))
                {
                    provjera = false;
                }
            }
            double dblString;
            if (deg == 0)
            {
                if (provjera == true)
                {
                    dblString = Convert.ToDouble(str.Replace(".", ","));
                    if (dblString >= 90 || dblString <= -90)
                    {
                        provjera = false;
                    }
                }
            }
            if (deg == 1)
            {
                if (provjera == true)
                {
                    dblString = Convert.ToDouble(str.Replace(".", ","));
                    if (dblString >= 180 || dblString <= -180)
                    {
                        provjera = false;
                    }
                }
            }
            return provjera;
        }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM