# Re: Having a difficult time with Case statements

**URL:** <https://www.ruby-forum.com/t/re-having-a-difficult-time-with-case-statements/147076>\
**Category:** Ruby\
**Created:** [August 28, 2008, 10:17am UTC](https://www.ruby-forum.com/t/re-having-a-difficult-time-with-case-statements/147076 "2008-08-28T10:17:47Z")\
**Posts on this page:** 1\
**Page:** 1

<div class="post-metadata">

**Author:** ![stickstone](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/6f9a4e/32.png) [@stickstone](https://www.ruby-forum.com/u/stickstone)\
**Post date:** [August 28, 2008, 10:17am UTC](https://www.ruby-forum.com/t/re-having-a-difficult-time-with-case-statements/147076/1 "2008-08-28T10:17:47Z")

</div>

> [http://www.ruby-forum.com/attachment/2623/startup.rb](http://www.ruby-forum.com/attachment/2623/startup.rb)

If you’re going to keep state in a local variable, then you need to keep  
looping within that method, because otherwise the value will be lost as  
soon  
as you return from it.

A much more common Ruby idiom for keeping state is to use an instance  
variable:

class Game  
def initialize  
@state = 0  
@playing = true  
end

```
def playing?
  @playing
end

def next_action
  case @state
  when 0
    puts "Nephlen".blue
    ...
    @state = 1
  ...
  end
end

```

end

g = Game.new  
while g.playing?  
g.next\_action  
end

This lets you create multiple game instances each with independent state  
(useful for a multi-player server!) and also makes unit testing much  
easier.

A neat trick to avoid the big case statement is to use dynamic method  
dispatch:

class Game  
def initialize  
@state = :startup  
end

```
def next_action
  send(@state) # calls the method name in the @state instance 

```

variable  
end

```
def startup
  puts "Hello!"
  puts "Moving to dungeon entrance"
  @state = :dungeon
end

def dungeon
  puts "You are in a deep dungeon. Go N/S/E/W?"
  case gets
  when /^n/i
    @state = :field
  when /^s/i
    @state = :tunnel
  when /^e/i
    @state = :monster
  when /^w/i
    @state = :monster
  else
    puts "Invalid selection"
  end
end

def monster
  puts "You have been eaten by a monster!"
end

... etc

```

end

For security reasons, make sure that an untrusted party can’t set the  
@state  
variable directly, e.g. by copying @state directly from a user input  
field  
or web form.

Regards,

Brian.
