-1

I am creating a CMD like program where the user manage his "drive" with commands. I would like to know if there is a way of doing this type of application in a easier/better way. Actually I'm doing like this:

Listing the commands

I created an enum with all commands to be easy to add and manage commands

Executing the command line

To know what command the user is trying to execute I get a list with the enum values and proceed to get the command in the list.

var list = ((Commands[])Enum.GetValues(typeof(Commands))).ToList();

var commandText = inputLine.Split(' ')[0];

if (list.Select(x => x.ToString().ToLower()).Contains(commandText))
{
    var command = list.FirstOrDefault(x => x.ToString().ToLower() == commandText);
    switch (command)
    {
        case Commands.List:
            Listar();
            break;
        case Commands.Go:
            Go();
            break;
    }
}

Edit:

The question came out wrong, I'm not trying to find a better way to solve the switch problem, I'm using it because it is a limited number of commands, so it make sense to use it. The answer I wanted was just a better way to make a Command Line Parser. Actually I'm in a competition where I don't have internet access, so no NuGet.

The way of getting the parameters seems bad too:

var temp = _line.Split('"').ToList();
var vals = new List<string>();

for (int i = 0; i < temp.Count; i++)
{
    if (i % 2 == 0)
        vals.AddRange(temp[i].Split('-').Select(x => x.Trim()));
    else
        vals.Add(temp[i]);
}


var path = _currentDirectory;

if (vals.Contains("p"))
    path = vals[vals.IndexOf("p") + 1];
  • There are a zillion command line parameter parsers available on NuGet, so I would only re-invent the wheel if you are doing it for education purposes only. And if you are unfamiliar with NuGet packages I recommend you learn about them as they are a really great tool to have in your toolbox of solutions. – Peter M Oct 30 '18 at 15:52
  • @PeterM: You understood my question the way I wanted, the problem is that I can't use NuGet in this situation. – Pancabiel Oct 30 '18 at 16:04
  • 1
    If you are in a competition with no internet access then how is what you are doing now not cheating? – whatsisname Oct 30 '18 at 16:21
  • @whatsisname I'm training, lol – Pancabiel Oct 30 '18 at 16:22
3

The main problem I see with this approach is extensibility.

If you wanted to add an extra command to the CMD application then you would need to add it to the enum and add a continuously growing number of elements in the switch statement. This will work for 10, 20, maybe more functions but what about when you have 100? Or 1000?

My suggestion would be to use an interface

public interface ICmd
{
  string CommandText {get; }
  void Execute(string[] args);
}

Then in your code you'd have:

var allCommands = GetAllLoadedCommands(); // probably via reflection
var cmd = allCommands.SingleOrDefault(c => c.Name == commandText);
if(cmd != null)
{
  cmd.Execute();
}

See this question for more details on the reflection bit.

By doing it this way all you'd need to do is implement a new version of the interface.

As an aside - nice work on enum GetValues(), I don't think this is the right place to do this but it's a good technique to know.

  • My problem was more of doing it with efficiency, the commands would not get that much big but your way may be better to implement. Thanks =) – Pancabiel Oct 30 '18 at 14:13
  • 4
    Realistically performance isn't likely to be your bottle neck here, it's a single user console application on a modern PC. Build for maintainability! – Liath Oct 30 '18 at 14:36

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.