Недавно я заметил ту же самую досадную проблему и решил написать синтаксический анализатор для синтаксического анализа массива аргументов командной строки.
Примечание: проблема в том, что аргументы .NET CommandLine, передаваемые статической функции void Main (string [] args), экранируются \ "и \\. Это сделано намеренно, поскольку вы, возможно, захотите передать аргумент, который имеет цитата или обратная косая черта в нем. Один пример:
скажем, вы хотите передать следующее в качестве одного аргумента:
-msg: Эй, "Где ты?"
например.
sampleapp -msg: "Привет, \" Где ты?
в? \ ""
Будет, как отправить его с поведением по умолчанию.
Если вы не видите причин, по которым кому-либо приходится экранировать кавычки или обратную косую черту для вашей программы, вы можете использовать собственный синтаксический анализатор для анализа командной строки, как показано ниже.
IE.
[program] .exe "C: \ test \" arg1 arg2
будет иметь аргументы [0] = c: \ test "arg1 arg2
То, что вы ожидаете, это args [0] = c: \ test \, а затем args [1] = arg1 и args [2] = arg2.
Следующая функция разбирает аргументы в список с помощью этого упрощенного поведения.
Обратите внимание, arg [0] - это имя программы с использованием приведенного ниже кода. (Вы вызываете List.ToArray () для преобразования результирующего списка в массив строк.)
protected enum enumParseState : int { StartToken, InQuote, InToken };
public static List<String> ManuallyParseCommandLine()
{
String CommandLineArgs = Environment.CommandLine.ToString();
Console.WriteLine("Command entered: " + CommandLineArgs);
List<String> listArgs = new List<String>();
Regex rWhiteSpace = new Regex("[\\s]");
StringBuilder token = new StringBuilder();
enumParseState eps = enumParseState.StartToken;
for (int i = 0; i < CommandLineArgs.Length; i++)
{
char c = CommandLineArgs[i];
// Console.WriteLine(c.ToString() + ", " + eps);
//Looking for beginning of next token
if (eps == enumParseState.StartToken)
{
if (rWhiteSpace.IsMatch(c.ToString()))
{
//Skip whitespace
}
else
{
token.Append(c);
eps = enumParseState.InToken;
}
}
else if (eps == enumParseState.InToken)
{
if (rWhiteSpace.IsMatch(c.ToString()))
{
Console.WriteLine("Token: [" + token.ToString() + "]");
listArgs.Add(token.ToString().Trim());
eps = enumParseState.StartToken;
//Start new token.
token.Remove(0, token.Length);
}
else if (c == '"')
{
// token.Append(c);
eps = enumParseState.InQuote;
}
else
{
token.Append(c);
eps = enumParseState.InToken;
}
}
//When in a quote, white space is included in the token
else if (eps == enumParseState.InQuote)
{
if (c == '"')
{
// token.Append(c);
eps = enumParseState.InToken;
}
else
{
token.Append(c);
eps = enumParseState.InQuote;
}
}
}
if (token.ToString() != "")
{
listArgs.Add(token.ToString());
Console.WriteLine("Final Token: " + token.ToString());
}
return listArgs;
}