What is wrong with my simple code here? - python

Hi I am having problems writing this simple program. I am just starting out with Python and was hoping for some help. When I run the start() function at the bottom of the programme, everything works fine until after the first raw_input(). If the user types "get coffee" for example, the string "Fair enough take a break" is printed but after this, rather than running the coffee() function like I would like, it just loops through to the start() function again.
Would someone be able to help please?
Thanks a lot.
def engine(next_scene):
scenes = {"start":start(),"coffee":coffee(),"work":work()}
return scenes[next_scene]
def start():
print "you are in the office"
print "you wonder what to do"
action = raw_input("what do you do? Get coffee or work?")
if action == "get coffee":
print "Fair enough take a break"
next_scene = "coffee"
engine(next_scene)
if action == "work":
print "Good man, you are well on your way to being a coder"
next_scene = "work"
engine(next_scene)
def coffee():
print "You walk out of the room"
print "You head down the stairs and into the cafe"
print "You order an espresso"
print "You neck it down"
print "Yumm"
print "You are wired"
action = raw_input("Now what? Work or go home? > ")
if action == "work":
print "You head back upstairs"
next_scene = "work"
engine(next_scene)
if action == "go home":
print "You lazy git"
def work():
print "You beaver away and become a cool coder"
next_scene = "start"
engine(next_scene)
start()

This
scenes = {"start":start(),"coffee":coffee(),"work":work()}
should be
scenes = {"start":start,"coffee":coffee,"work":work}
You called the functions in the dictionary definition, but you just want to get the function object.

Your engine function should like.
def engine(next_scene):
scenes = {"start":start,"coffee":coffee,"work":work}
scenes[next_scene]()

Related

How to return to beginning of loop?

search_room = raw_input("Search the:")
if search_room == "classroom":
print "You quitly make your way to the classroom, which is empty besides last night's homework"
sleep(3)
print "Enter 'inspect' into the command line to inspect the homework, or enter exit, to return to the kitchen."
action = raw_input("Command:")
if action == "inspect":
print "Hmph, uncompleted. Thats strange."
print "Enter 'inspect' into the command line to inspect the homework, or enter exit, to return to the kitchen."
action = raw_input("Command:")
if action == "exit":
print "you return to the kitchen"
search_room = raw_input("Search the:")
if action == "classroom":
I'm trying to figure out how to have this loop so i one could travel back and forth between the kitchen and the classroom, but if I try to go back to the classroom after exiting, I get an error message regarding a later 'for loop'.
If I understand your question correctly, your trying to figure out how to set up a loop that will let you go from kitchen back to classroom and so on and so forth without needing to nest an infinite amount of conditionals. I suggest you have an outer while(true) loop power the sequence of steps, and add conditions to check if a move is valid (to go to to the kitchen you must currently be in the classroom and have entered exit, ect)
You need to put the code block inside its own loop with a simple boolean sentinel value (while not stop) and if stop is set to true at any point, the otherwise endless loop will stop. Also remember the importance of python indentations for distinguishing code scopes, different from languages like java where it doesn't matter where you put the code as long as it is between the { }. Also consecutive if statements will each be executed individually unless you use if..elif which is what I think you want because you are comparing the same variable in the same scope.
Also if you have more than two rooms, like something in the game Clue, you should define some sort of scoping for each room. If you are in a room, which rooms can you access from there? I did this just with a simple dictionary scopes where each room is associated with a list of rooms it can access which is verified on getting search_room. They only have access to each other right now, but you can add more to each list to increase scope to other rooms (and add more if branches)
stop = false;
scopes = {"kitchen": ["classroom"], "classroom": ["kitchen"]}
locCur = "kitchen" #starting room
locPrev = "kitchen"
while not stop:
search_room = raw_input("Search the:")
if scopes[locCur].index(search_room) > -1 : #validate the room choice
if search_room == "classroom":
locCur = "classroom" #update current scope
print "You quietly make your way to the classroom, which is empty besides last night's homework"
sleep(3)
print "Enter 'inspect' into the command line to inspect the homework, or enter exit, to return to the kitchen."
action = raw_input("Command:")
if action == "inspect":
print "Hmph, uncompleted. Thats strange."
print "Enter 'inspect' into the command line to inspect the homework, or enter exit, to return to the kitchen."
action = raw_input("Command:")
if action == "inspect":
#print/do something else
elif action == "exit":
locCur = locPrev #set scope back to what it was
print "you return to the " + locPrev
locPrev = "classroom" #store this location
continue
elif search_room == "kitchen":
#do something for this room
print "message"
continue
elif search_room == "some other room":
#do something for this room
continue
elif search_room == "stop":
stop = true

calling method outside class python

I'm relatively new to Python and OOP, I'm trying to write a mini adventure game with classes and have gotten stuck with my BattleEngine class.
The idea is to have options to fight or outwit an opponent based on your characters and the opponents 'strength' and 'wit'.
I get an error when I try to call my attack method here:
class Armory(Scene):
def enter(self):
print "This room appears to be some kind of armory. There are shelves full of weaponry lining"
print "the walls. You walk around admiring the shiny weapons, you reach out to pick up a"
print "massive battleaxe. Right as your fingers touch it you hear voices from behind the"
print "next door. They sound like they're getting closer. As the voices grow nearer you must make"
print "a decision. Will you stand and fight (enter 'fight') or will you use your wit to outsmart"
print "your opponent(enter 'wit')?"
decision = raw_input("> ")
battle = BattleEngine()
if decision == "fight":
attack(self, Player.strength, 3)
if player_wins:
print "A man in light armour walks in and sees you with your sword drawn. A look of"
print "shock and disbelief is on his face. You act quickly and lunge at him."
print "The soldier struggles to unsheath his sword as you run him through."
print "He collapses to the ground wearing the same look of disbelief."
print "Your strength has increased by 1."
Player.strength += 1
elif decision == "wit":
outwit(self, Player.wit, 3)
Here is where I defined my BattleEngine class:
class BattleEngine(object):
def attack(self, player_strength, nonplayer_strength):
player_roll = randint(1,6)
nonplayer_roll = randint(1,6)
if (player_roll + player_strength) >= (nonplayer_roll + nonplayer_strength):
return player_wins
else:
return 'death'
def outwit(self, player_wit, nonplayer_wit):
player_roll = randint(1,6)
nonplayer_roll = randint(1,6)
if (player_roll + player_wit) >= (nonplayer_roll + nonplayer_wit):
return player_wins
else:
return 'death'
Once I get to this point in my program is receive the error that : 'attack global name is not defined'
I'm not sure what I'm doing wrong exactly. Any help would be fantastic!
You need to call attack on your BattleEngine instance, and you do not need to pass in self:
battle = BattleEngine()
if decision == "fight":
player_wins = battle.attack(Player.strength, 3)
Note that you need to receive the return value of the .attack() method.
The same applies to the .outwit() method further on:
elif decision == "wit":
player_wins = battle.outwit(Player.wit, 3)
You probably need to fix the return values in the .attack() and .outwit() methods; instead of return player_wins and return 'death', return True or False perhaps.
The self parameter is taken care of for you by Python, and will refer to the specific BattleEngine instance.
Not that you really need classes here, your BattleEngine() class currently has no per-instance state, for example. You don't use self in any of the methods, because there is nothing on the instance to refer to.

How to make a function change the True/False statements for other functions

Here's the basic idea I'm having trouble with: I'm trying to make a simple game where you are in one room and you have 2 rooms branching from the first that need to be "completed" before continuing. I want the 2'nd and 3'rd room to change my original True statements to False statements that all need to be switched before proceeding in the game.
from sys import exit
def room_1():
print "You're in room one, there are two doors to room 2 and 3."
print "Where do you want to go?"
done_2=True
done_3=True
while True:
move=raw_input("'room 2' or 'room 3'? >")
if move == 'room 2':
room_2()
elif move == 'room 3':
room_3()
else:
print "not a valid answer"
print "You Win!"
exit(0)
def room_2():
print "You finished room 2!"
done_1=False
raw_input('Press button')
room_1()
def room_3():
print "You finished room 3!"
raw_input('press button')
done_3=False
room_1()
room_1()
How do I change the done_ statements from within rooms 2 and 3?
~
In Python, you have to declare global variables before you can assign to them; otherwise, any assignment will shadow the global variable.
def room_2():
global done_1 # <- right here
print "You finished room 2!"
done_1=False
raw_input('Press button')
room_1()
def room_3():
global done_3 # <- right here
print "You finished room 3!"
raw_input('press button')
done_3=False
room_1()
However!
This is generally bad style, especially for such a simple case as this. It makes it more difficult to reason about how your functions work, what they change, and in what order.
It'd be much easier, more readable, and simpler to just return True or False from your functions as needed.
If you try to think of your functions as "black boxes" which have inputs, and guarantee certain outputs, it will generally help in avoiding many confusing bugs that can arise.
You need to declare done_1 and done_2 as global variables, outside of function room_1()

changing response based on variable

I'm trying to figure out how to use an if statement before the assignment to change it is made. The point of this script is to check if the knife is taken before it prompts with the question to take it from the table. It's to make it so that you can walk back to the table and get another response if you've already taken it. What am I doing wrong?
def table ():
if knife_taken == False:
print "it's an old, brown wooden table, and atop it you find a knife"
print "Will you take the knife or go back?"
knife = raw_input ("> ")
if knife.strip().lower() in ["back", "b", "no"]:
basement2()
elif knife.strip().lower() in ["take knife", "knife", "yes", "k"]:
knife_taken = True
print "You now have the knife, good, you are going to need it"
raw_input()
basement2()
else:
print "I did not understand that."
raw_input()
table()
else:
print "There's nothing on the table"
raw_input()
basement2()
Basically when you change the variable knife_taken in your function you change it at a local level, this means when the function ends the changes are lost. There are two ways to fix this either use global (but thats the bad way)
global knife_taken
knife_taken = True
Or you can return the state of the knife from the function
return knife_taken
# later on
kitchen(knife_taken)
and store it in a variable, passing it back to kitchen later as an arguement
Or as an extra little bonus, you can store game state in a dictionary. You could then update the dictionary as the game state changes e.g.
game_state = {}
game_state['knife_taken'] = False
def kitchen():
if not game_state['knife_taken']:
print "Take the knife!"
game_state['knife_taken'] = True
else:
print "Nothing to see here."
kitchen()
kitchen()

I'm making a python text-adventure. Need help making an 'inventory'

I'm making a python text adventure. It is based off of ex41 in Learn Python the Hard Way, so it is somewhat similar. My question, however, has nothing to do with that exercise. I'm trying to make an inventory so that an item can be picked up and used (i.e. a key or febreeze).
At first my plan was to use a Boolean variable so that when the item was 'picked up' it would set a value to True, but it doesn't seem to be working. I think that the problem is that the value resets once I leave the room.
Now I'm trying a list and when the item is 'picked up' the item is appended into the inventory list.
How can I make an inventory, or at least 'pick up' an item and then later 'use' it?
The lines of code that I think are important to look at are 18-20 (under the def __init__(self, start)), 77(under the def cell(self)), 161-162(under the def janitor(self)).
from sys import exit
from random import randint
import time
prompt = '> '
class Game(object):
def __init__(self, start):
self.quips = [
"Way to go, you died."
"Now you're dead. Sweet.",
"Well isn't this just peachy? You're dead. (It's not peachy.)"
]
self.start = start
#self.smell = 0
#self.Febreeze = False
#self.key = False
self.inventory = []
#if self.smell >=2:
# return 'death'
def play(self):
next = self.start
while True:
print "\n-------"
room = getattr(self, next)
next = room()
def death(self):
print self.quips[randint(0, len(self.quips)-1)]
exit(1)
def intro(self):
print "You wake up."
print "You're in a dark cell."
print "You have no idea who you are or where you are."
print "The door is slightly open."
print "You stagger through the door. The light is blinding."
print "You have just escaped imprisonment and you're on the run."
return 'central_corridor'
def central_corridor(self):
print "In front of you is a long corridor with no doors on the side, but you think you can make out a door at the very end."
print "Behind you is the cell that you have just escaped."
next = raw_input(prompt)
if "cell" in next:
print "You decide to go back into your cell."
return 'cell'
elif "forward" in next:
print "You travel down the corridor towards the door."
return 'front_corridor'
else:
print "That command doesn't exist."
return 'central_corridor'
def cell(self):
print "You're standing in the middle of a musty cell."
print "There is a bed in the corner with a rotting mattress."
print "Under the bed the bricks are loose."
print "In the opposite corner there is a dirty toilet that implies that prison food is even worse than Taco Bell."
print "There are some scratches on the wall next to the toilet."
print "Behind you is an exit into the corridor."
next = raw_input(prompt)
if "toilet" in next:
print "It'd probably be best if this toilet wasn't described."
#self.smell = self.smell + 1
return 'cell'
elif "febreeze" in next and "Febreeze" in self.inventory #and self.Febreeze = True:
print "You use the Febreeze on the toilet to get rid of the odor."
print "Now you can go behind the toilet to read the rest of the scratches."
elif "scratches" in next:
print "The scratches on the wall seem to be tally marks. It goes up to 123. I wonder what it means."
print "You see more scratches behind the toilet, but the stench is too much for you to handle."
print "If only you could get rid of the smell..."
#self.smell = self.smell + 1
return 'cell'
elif "bed" in next:
print "There are various stains on the mattress. Some of the springs are poking up into the mattress. Ouch."
print "Buried between the wall and the mattress is a stuffed animal."
return 'cell'
elif "bricks" in next:
print "You pull the bricks out of the floor and find a few pieces of toilet paper."
print "There is a note written on them in what you hope is dried blood."
print "The note reads:\n -------------------------\nthe closet!! the closet in the walls i'm not \nsure\twhich one it is but its defin-\nly in the hall. i hear it in the bricks!\n---------------------------"
print "Hmm, maybe it's a hint or something."
elif "corridor" in next:
return 'central_corridor'
else:
print "I do not understand how to %s" % next
return 'cell'
def front_corridor(self):
print "You are standing in front of a door."
print "On the side of the door is a keypad."
next = raw_input(prompt)
if "keypad" in next:
return 'keypad'
elif "wall" in next:
return 'wall'
elif "back" in next:
return 'central_corridor'
else:
print "I don't understand %s" % next
return 'front_corridor'
def wall(self):
print "Which wall do you want to check?"
next = raw_input(prompt)
if "left" in next:
return 'left'
elif "right" in next:
return 'right'
elif "back" in next:
return 'front_corridor'
def right(self):
print "You examine the wall carefully, running your fingers across each of the bricks."
print "Unfortunately it doesn't look like anything of value is in this wall."
print "Well, you just wasted some time."
return 'wall'
def left(self):
print "You examine the wall carefully, running your fingers across each of the bricks."
print "One of the bricks seems to be protruding from the wall."
print "Do you push it?"
next = raw_input(prompt)
if next[0] == "y":
print "A few of the bricks shift, revealing a secret door way."
return 'janitor'
elif next[0] == "n":
print "You decide not to push the brick. Good thinking, it may have been a booby trap."
return 'front_corridor'
else:
print "That doesn't exactly make sense..."
return 'wall'
def janitor(self):
print "You are in a room filled with janitorial tools."
print "On your left you see a few cans of Febreeze, a plunger and a Playboy magazine."
next = raw_input(prompt)
if "febreeze" in next:
print "You pick up some Febreeze and put it in your back pocket."
print "Maybe this will be useful somewhere down the line."
self.inventory.append("Febreeze")
#self.Febreeze = True
return 'janitor'
elif "plunger" in next:
print "You try to pick up the plunger but it appears to be stuck in the ground."
print "After tugging for a few minutes the handle comes out, leaving the rubber suction cup plastered to the floor."
print "Who knows what's keeping it there."
print "You decide not to touch it."
return 'janitor'
elif "playboy" in next:
print "Well isn't that nice."
print "These janitors certainly have good taste."
return 'janitor'
elif "back" in next:
return 'front_corridor'
else:
print "Do WHAT with WHAT?"
return 'janitor'
def keypad(self):
print "Above the keypad there is a sign that reads:\n-----------\nInput a 3 digit code.\nWarning: If code is incorrect 3 times, keypad will self-destruct.\n-----------"
code = "%d%d%d" % (randint(1,9), randint(1,9), randint(1,9))
guess = raw_input("Password: ")
guesses = 0
while guess != code and guesses < 2:
print "BZZZZZEDD!"
guesses += 1
guess = raw_input("Password: ")
if guess == code:
print "The keypad beeps in acceptance. Wow, that was a good guess"
print "The door swings open."
print "Behind the door is a long bridge suspended over a lake of lava."
return 'bridge'
elif "key" in guess and key == True:
print "You flash your card key across the keypad."
print "There is a beep as the door swings open."
print "Behind the door is a long bridge suspended over a lake of lava."
return 'bridge'
else:
print "The keypad buzzes one last time and then you hear a sickening melting"
print "sound as the lock mechanism fuses together."
print "There is a small clicking while the keypad countsdown."
print "3"
time.sleep(1)
print "2"
time.sleep(1)
print "1"
time.sleep(1)
print "There is a large explosion and you are caught right in the middle of it."
print "The fiery blast tears your skin from your body as you scream in agony."
return 'death'
def bridge(self):
print "You carefully walk onto the bridge."
print "One false move and you could be dead."
print "Across the bridge is a door leading to the outside world."
next = raw_input(prompt)
if "jump" in next:
print "You jump to your death."
print "Probably not the best idea."
elif "run" in next:
print "You run"
a_game = Game("intro")
a_game.play()
Your approach seems to work fine, but you have a couple of bugs. In cell(), you need a : after the elif "febreeze"... statement (before the comment starts). Also, at the end of that elif block, you need to return 'cell'. With these changes, I can pick up the Febreeze and use it.
If you define the inventory as a list(that's what I did), then you can do:
class Attributes:
def __init__(self, inventory):
self.inventory = inventory
Player = Attributes([])
Player.inventory.append("Febreeze")
The square brackets make the inventory, and the "append" adds Febreeze to it.
if you tryed to define it as a list e.g (guessing this is on python)
def inventory[]
inventory.append
add item (inventory)
cannot rember how to add it to the inventory but there is the basics

Categories