Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/regex/16.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# [0-9]-[0-9]-[0-9]的匹配模式,但不匹配[0-9]-[0-9]_C#_Regex - Fatal编程技术网

C# [0-9]-[0-9]-[0-9]的匹配模式,但不匹配[0-9]-[0-9]

C# [0-9]-[0-9]-[0-9]的匹配模式,但不匹配[0-9]-[0-9],c#,regex,C#,Regex,我不知道如何用正则表达式来实现这一点(或者如果可以,我对正则表达式还不熟悉)。我有一个用户将输入的角度值,我正在尝试验证输入。它的形式是度分秒。我遇到的问题是,如果用户错误地键入秒数部分,我必须捕获该错误,但我的匹配度分钟是成功的 也许这种方法能更好地解释: private Boolean isTextValid(String _angleValue) { Regex _degreeMatchPattern = new Regex("0*[1-9]");

我不知道如何用正则表达式来实现这一点(或者如果可以,我对正则表达式还不熟悉)。我有一个用户将输入的角度值,我正在尝试验证输入。它的形式是度分秒。我遇到的问题是,如果用户错误地键入秒数部分,我必须捕获该错误,但我的匹配度分钟是成功的

也许这种方法能更好地解释:

    private Boolean isTextValid(String _angleValue) {

        Regex _degreeMatchPattern = new Regex("0*[1-9]");
        Regex degreeMinMatchPattern = new Regex("(0*[0-9]-{1}0*[0-9]){1}");
        Regex degreeMinSecMatchPattern = new Regex("0*[0-9]-{1}0*[0-9]-{1}0*[0-9]");

        Match _degreeMatch, _degreeMinMatch, _degreeMinSecMatch;

        _degreeMinSecMatch = degreeMinSecMatchPattern.Match(_angleValue);
        if (_degreeMinSecMatch.Success)
            return true;

        _degreeMinMatch = degreeMinMatchPattern.Match(_angleValue);
        if (_degreeMinMatch.Success)
            return true;

        _degreeMatch = _degreeMatchPattern.Match(_angleValue);
        if (_degreeMatch.Success)
            return true;

        return false;
    }
}
如果度-分-秒匹配不成功,我想检查度-分,但前提是用户没有输入任何秒数据。我可以通过正则表达式来实现这一点,还是需要解析字符串并分别计算每个部分?谢谢

编辑:样本数据将为45-23-10作为正确数据。问题是45-23也是有效数据;0秒是可以理解的。因此,如果用户在意外情况下键入45-23-1=,则代码中的degreeMatchPattern regex将成功匹配,即使它无效


第二次编辑:为了清楚起见,分钟和第二部分都是可选的。用户可以键入45,这是有效的。

也许您最好只解析输入并单独检查is片段。

我不确定我是否理解正确,但我认为

(?<degrees>0*[0-9])-?(?<minutes>0*[0-9])(?:-?(?<seconds>0*[0-9]))?$
(?0*[0-9])-?(?0*[0-9])(?:-?(?0*[0-9]))$
可能有用

但这是相当含糊的;另外,我想知道为什么只允许一位数的度/分/秒值。请给出一些您想匹配和不想匹配的示例。

您可以使用
{m,}
语法指定“模式的此部分必须至少匹配3次”。由于每个组件之间都有连字符,请分别指定第一部分,然后可以在以下情况下将每个连字符数字组合组合组合在一起:

`[0-9](-[0-9]){2,}`

您还可以将
[0-9]
缩短为
\d
\d(-\d){2,}
首先,正则表达式中的字符默认匹配一次,因此{1}是多余的

其次,由于您显然可以隔离此值(您只提示输入此值,而不必在输入数据的段落中查找),因此您应该在字符串中包含“^”和“$”,以强制该字符串只包含此模式

请尝试“^\d{1,3}-\d{1,2}(-\d{1,2})?$”

分解:^匹配字符串的开头\d匹配任何一个十进制字符,然后在后面指定{1,3},它将匹配任何数字的一到三个匹配项。然后你要寻找一个破折号,然后是一个类似的十进制模式,但只有一两次。最后一项用括号括起来,这样我们就可以把字符分组了。它的形式类似于前两个,那么有一个?它将前面的字符组标记为可选。末尾的$表示输入应该结束。因此,它将匹配222-33-44或222-33,但不匹配222-3344或222-33-abc


请记住,您可能需要合并其他规则。例如,秒可以表示为十进制(如果您希望分辨率小于1秒)。您可能需要选择小数点和一个或多个附加数字。此外,您可能有一个最大度数值;上述正则表达式将匹配最大整数DMS值359-59-59,但它也将匹配无效的999-99-99。您可以使用正则表达式来限制最大值(例如“(3[0-5]\d|[1-2]\d{2}|\d{1,2})”将匹配0到359之间的任何数字,方法是匹配一个3,然后是0-5,然后是0-9,或任何以1或2开头的3位数字,或任何两位数字),但如示例所示,正则表达式将变得冗长而混乱,因此,请用代码很好地记录您正在做的事情。

也许您应该尝试类似的方法,并测试空组/无效组:

Regex degrees = new Regex(
                @"(?<degrees>\d+)(?:-(?<minutes>\d+))?(?:-(?<seconds>\d+))?");
string[] samples = new []{ "123", "123-456", "123-456-789" };
foreach (var sample in samples)
{
    Match m = degrees.Match(sample);
    if(m.Success)
    {
        string degrees = m.Groups["degrees"].Value;
        string minutes = m.Groups["minutes"].Value;
        string seconds = m.Groups["seconds"].Value;
        Console.WriteLine("{0}°{1}'{2}\"", degrees,
            String.IsNullOrEmpty(minutes) ? "0" : minutes,
            String.IsNullOrEmpty(seconds) ? "0" : seconds
        );
    }
}
Regex度=新的Regex(
@“(?\d+)(:-(?\d+))(?:-(?\d+))”;
字符串[]samples=new[]{“123”、“123-456”、“123-456-789”};
foreach(样本中的var样本)
{
匹配m=度。匹配(样本);
如果(m.成功)
{
字符串度数=m.组[“度数”].值;
字符串minutes=m.Groups[“minutes”].Value;
字符串秒=m.Groups[“seconds”].值;
Console.WriteLine(“{0}°{1}'{2}\”,度,
String.IsNullOrEmpty(分钟)?“0”:分钟,
String.IsNullOrEmpty(秒)?“0”:秒
);
}
}

你有一些样本数据吗?它是45-23-1=。我想你只是没有看到等号。也许更好的例子是45-23-1A。很抱歉混淆了。我想他想匹配2或3个数字,但只有在没有后面的情况下才匹配2个数字,而不是在后面有无效输入的情况下匹配2个数字。只需稍作修改(因为三者中的第二个也是可选的,C#需要第二个反斜杠来正确地转义d)这是有效的。我的最终表达式是“^\\d{1,3}(-\\d{1,2}(-\\d{1,2}”)?$”。谢谢!如果在打开字符串的双引号前面放一个@,NET将自动转义任何需要它的字符。这对文件很有用(反斜杠目录分隔符)和多行数据(\r\n无处不在)以及正则表达式。今天我还学到了一些其他内容(我知道多行数据,但不知道正则表达式)。谢谢!