0

日、時間、分、秒の数を表す整数{n}d {n}h {n}m {n}sであるとして入力できる文字列があります。文字列からこの番号{n}を抽出するにはどうすればよいですか?{n}

ユーザーは、4-d、h、m、sのすべてを入力する必要はありません。彼は4日を意味する4dまたは5時間2秒を意味する5時間2秒しか入力できませんでした。

これが私が持っているものです。間違いなく、これを行うためのより良い方法があるはずです。また、すべてのケースを網羅しているわけではありません。

int d; int m; int h; int sec;
string [] split = textBox3.Text.Split(new Char [] {' ', ','});
List<string> myCollection = new List<string>();

foreach (string s in split)
{
    d = Convert.ToInt32(s.Substring(0,s.Length-1));
    h = Convert.ToInt32(split[1].Substring(1));
    m = Convert.ToInt32(split[2].Substring(1));
    sec = Convert.ToInt32(split[3].Substring(1));
}
dt  =new TimeSpan(h,m,s);
4

5 に答える 5

3

日、時間、分、秒の順序が固定されている場合は、正規表現を使用できます。

string input = textBox3.Text.Trim();
Match match = Regex.Match(input,
    "^" +
    "((?<d>[0-9]+)d)? *" +
    "((?<h>[0-9]+)h)? *" +
    "((?<m>[0-9]+)m)? *" +
    "((?<s>[0-9]+)s)?" +
    "$",
    RegexOptions.ExplicitCapture);

if (match.Success)
{
    int d, h, m, s;
    Int32.TryParse(match.Groups["d"].Value, out d);
    Int32.TryParse(match.Groups["h"].Value, out h);
    Int32.TryParse(match.Groups["m"].Value, out m);
    Int32.TryParse(match.Groups["s"].Value, out s);
    // ...
}
else
{
    // Invalid input.
}
于 2012-06-24T20:28:58.143 に答える
0

ここにはさまざまなオプションがあります。TimeSpan.TryParse関数を使用することもできますが、これには別の入力形式が必要です。別のアプローチは、空白で文字列を分割し、各部分を反復処理することです。その際、パーツにdhsなどが含まれているかどうかを確認し、値を目的の変数に抽出できます。RegExを使用して文字列を解析することもできます。反復に基づく例を次に示します。

    static void Main(string[] args)
    {
        Console.WriteLine("Enter the desired Timespan");
        string s = Console.ReadLine();

        //ToDo: Make sure that s has the desired format

        //Get the TimeSpan, create a new list when the string does not contain a whitespace.
        TimeSpan span = s.Contains(' ') ? extractTimeSpan(new List<string>(s.Split(' '))) : extractTimeSpan(new List<string>{s});

        Console.WriteLine(span.ToString());

        Console.ReadLine();
    }

    static private TimeSpan extractTimeSpan(List<string> parts)
    {
        //We will add our extracted values to this timespan
        TimeSpan extracted = new TimeSpan();

        foreach (string s in parts)
        {
            if (s.Length > 0)
            {
                //Extract the last character of the string
                char last = s[s.Length - 1];

                //extract the value
                int value;
                Int32.TryParse(s.Substring(0, s.Length - 1), out value);

                switch (last)
                {
                    case 'd':
                        extracted = extracted.Add(new TimeSpan(value,0,0,0));
                        break;
                    case 'h':
                        extracted = extracted.Add(new TimeSpan(value, 0, 0));
                        break;
                    case 'm':
                        extracted = extracted.Add(new TimeSpan(0, value, 0));
                        break;
                    case 's':
                        extracted = extracted.Add(new TimeSpan(0, 0, value));
                        break;
                    default:
                        throw new Exception("Wrong input format");
                }
            }
            else
            {
                throw new Exception("Wrong input format");
            }
        }

        return extr
于 2012-06-24T20:16:31.390 に答える
0

カスタムパーサーを作成します-ステートマシンを使用して、文字列の各部分が正確に何であるかを判別します。

アイデアは、文字列内の各文字を繰り返し処理し、それが何であるかに応じて状態を変更することです。したがって、状態NumberDay、、、、状態、Monthおよび状態があります。HourSecondsSpaceStart End

于 2012-06-24T20:10:36.493 に答える
0

1つのアプローチは、を使用するsscanf()ことです。これは、これを非常に簡単に実行します。この記事では、この関数のバージョンをC#で実装しました。

潜在的な構文エラーをより適切に処理する必要がある場合は、独自のパーサーを実装するだけです。私は、各キャラクターを1つずつ調べるだけでそれを行います。

于 2012-06-24T20:11:30.393 に答える
0

アプローチを少し洗練することができます

int d = 0;
int m = 0;
int h = 0;
int s = 0;

// Because of the "params" keyword, "new char[]" can be dropped.
string [] parts = textBox3.Text.Split(' ', ',');

foreach (string part in parts)
{
    char type = part[part.Length - 1];
    int value = Convert.ToInt32(part.Substring(0, part.Length - 1));
    switch (type) {
        case 'd':
            d = value;
            break;
        case 'h':
            h = value;
            break;
        case 'm':
            m = value;
            break;
        case 's':
            s = value;
            break;
    }
}

これで、不足していないパーツが正確に設定されました。不足している部分はまだ0です。TimeSpan値をでに変換できます

var ts = TimeSpan.FromSeconds(60 * (60 * (24 * d + h) + m) + s);

これはすべての場合をカバーします!

于 2012-06-24T20:38:05.567 に答える