Using Dictionaries in Python in place of Case/Switch statement

dictionary, python, random, rubiks-cube

Solution

When you define the dict, it's actually calling the functions, and storing the return value in the dictionary. To just have the dictionary store a reference to the functions, you need to drop the trailing parentheses. So something like:

scramble = {  0: self.up_turn,
              1: self.down_turn,
              etc.

Then, at the bottom, call `scramble[i]()`.

This will call the function with no arguments. To handle the case where you pass "inverted" as an argument, you could either define separate functions like up_turn_inverted(), etc., or you could have the dictionary store a 2-ple consisting of the function, and the argument, then call something liks `scramble[i][0](scramble[i][1])`

Update from suggestion in comments: You could also use lambda expressions to define the functions, particularly the ones that require an argument. This is basically equivalent to defining an up_turn_inverted function, but done in-place as an anonymous function. It would look like this:

6: lambda: self.up_turn("inverted")
7: lambda: self.down_turn("inverted")

etc.

Problem

I want to randomize a rubik's cube that is initialized as complete (all colors on the correct sides). I have move functions that rotate the cube. I want to randomly pick 50 functions in a row to properly randomize it. I am doing this project to learn a little bit more about Python, since I mostly do C++ and I see there is no case/switch for Python, so I am trying a dictionary. When I make the dictionary, the code seems to execute for some reason: ``` def random_cube(self): scramble = { 0 : self.up_turn(), 1 : self.down_turn(), 2 : self.left_turn(), 3 : self.right_turn(), 4 : self.front_turn(), 5 : self.back_turn(), 6 : self.up_turn("inverted"), 7 : self.down_turn("inverted"), 8 : self.left_turn("inverted"), 9 : self.right_turn("inverted"), 10: self.front_turn("inverted"), 11: self.back_turn("inverted") } for x in range(50): i = random.randint(0,11) scramble[i] ``` So when I make this dictionary, it seems to run through and execute all 11 entries for some reason (I think). I can't seem to find a better way, at least more elegant than a long if/elif string of statements. !EDIT: Implementing both suggestions, the ("inverted") flag for the functions are not being set by either suggestion. For example, calling 1 and 7 both give me down_turn, but the output shows that the flag was not set when it should have been on number 7. Any ideas?

Original source