Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Better way to handle switch case in C#

I do apologize in advance if my question looks really dumb, but for some reason I can't look through more graceful solution to the problem. So I have a method that utilizes switch - case blocks similar to the below chunk of code:

public enum Items
{
    item_1, item_2, item_3, .... item_N
};

private string String_1 {get; set;}
private string String_2 {get; set;}
private string String_3 {get; set;}
// ...
private string String_N {get; set;}

public void DoSomething(Items item){
    switch(item){
        case item_1:
            MethodNumberOne();
            MethodNumberTwo();
            MethodNumberThree();
            Console.WriteLine($"{0} is displayed on the page", String_1);
            break;

        case item_2:
            MethodNumberOne();
            MethodNumberTwo();
            MethodNumberThree();
            Console.WriteLine($"{0} is displayed on the page", String_2);
            break;

        case item_3:
            MethodNumberOne();
            MethodNumberTwo();
            MethodNumberThree();
            Console.WriteLine($"{0} is displayed on the page", String_3);
            break;
        // ...
        case item_N:
            MethodNumberOne();
            MethodNumberTwo();
            MethodNumberThree();
            Console.WriteLine($"{0} is displayed on the page", String_N);

As it can be seen from the above example switch statement is calling the same methods, and the only difference is the last Console call.

My question: is there a more elegant way to handle this situation as I don't really like the duplication of the code. So far I tried to carry out Items enum to separate class and pass this as parameter, but this approach doesn't work as static class can't be passed as parameter in C#

public static class Items {
    public string String_1 {get; set;}
    public string String_2 {get; set;}
    public string String_3 {get; set;}
    // ...
    private string String_N {get; set;}
}

// ....

public void DoSomething(Items item)
  • not allowing to declare this method

Any suggestions are greatly appreciated..

like image 943
TiredOfProgramming Avatar asked Sep 12 '25 15:09

TiredOfProgramming


2 Answers

You could store the enum Items to String_X mapping in a dictionary rather than relying on a switch.

private IDictionary<Items, string> _itemStringMap = new Dicitionary<Items, string>()
{
   { Items.item_1, String_1 },
   //Other items here
};

public void DoSomething(Items item)
{
  var s = _itemStringMap[item];

  MethodNumberOne();
  MethodNumberTwo();
  MethodNumberThree();
  Console.WriteLine($"{0} is displayed on the page", s);
}

You may want to check that the item argument has a valid mapping and if not use a default string.

like image 64
Nick Williams Avatar answered Sep 14 '25 04:09

Nick Williams


The simplest way to clean this up is to introduce a variable.

public void DoSomething(Items item){

    string foo;
    switch(item){
        case item_1:
            foo = String_1;
            break;

        case item_2:
            foo = String_2;
            break;

        case item_3:
            foo = String_3;
            break;
        // ...
        case item_N:
            foo = String_N;
            break;
    }

    MethodNumberOne();
    MethodNumberTwo();
    MethodNumberThree();
    Console.WriteLine($"{0} is displayed on the page", foo);

}

This makes it clear that what we really have is a key/value pair though, so we can go farther and store the strings in a dictionary.

var dict = new Dictionary<Items,string>()
{
    { item_1, string_1 },
    { item_2, string_2 },
    //...
    { item_N, string_N }
}

MethodNumberOne();
MethodNumberTwo();
MethodNumberThree();
Console.WriteLine($"{0} is displayed on the page", dict[item]);

Of course, you'll want to make sure the key (item) is valid, error handling, and all that jazz.

like image 28
RubberDuck Avatar answered Sep 14 '25 03:09

RubberDuck