2016-07-29 153 views
0

程序問題應該更新每一次全局變量int_choice值的玩家分數(這是一個乒乓球比賽)與全局變量設置

int_choice只能值1或0。如果它是1,功能left_or_right「告訴」球右轉,如果它是0,則球左轉。

int_choice在幾個地方更新:在開始它初始化,然後在left_or_right()功能,然後在draw()功能。

每次用戶打分時,球應該從桌子中心向該用戶重新分娩,但球始終在同一方向再次出現兩次,然後在相反方向再次出現兩次,依此類推,無論誰是最後一個得分。

下面的代碼:存在

import random 

int_choice = random.randint(0,1) 
direc = None 

def left_or_right(): 
    global direc, int_choice 
    if int_choice == 0: 
     direc = "LEFT" 
    elif int_choice == 1: 
     direc = "RIGHT" 
    return direc 

def spawn_ball(direction): 
    left_or_right() 
    global ball_pos, ball_vel # these are vectors stored as lists 
    ball_pos = [WIDTH/2, HEIGHT/2] 
    if direction == "LEFT": 
     ball_vel[0] = (random.randrange(12, 25)*(-0.1)) 
     print "Velocity[0]: ", ball_vel[0] 
     ball_vel[1] = (random.randrange(6, 19)*(-0.1)) 
    elif direction == "RIGHT": 
     ball_vel[0] = (random.randrange(12, 25)*(0.1)) 
     print "Velocity[0]: ", ball_vel[0] 
     ball_vel[1] = (random.randrange(6, 19)*(-0.1)) 
     print "Velocity[1]: ", ball_vel[1] 

def new_game(): 
    global paddle1_pos, paddle2_pos, paddle1_vel, paddle2_vel, direc 
    global score1, score2, 
    spawn_ball(direc) 
    score1 = 0 
    score2 = 0 

def draw(canvas): 
    global remaining_names, score1, score2, paddle1_pos, paddle2_pos,   ball_pos, ball_vel, BALL_RADIUS, direc 
    global int_choice 


    # update ball 
    ball_pos[0] += ball_vel[0] 
    ball_pos[1] += ball_vel[1] 
    if ball_pos[1] - BALL_RADIUS <= 0: 
     ball_vel[1] = ball_vel[1] + (ball_vel[1] * (-2))  
    elif ball_pos[1] + BALL_RADIUS >= HEIGHT: 
     ball_vel[1] = ball_vel[1] + (ball_vel[1] * (-2)) 
    elif ball_pos[0] - BALL_RADIUS <= (0 + PAD_WIDTH): 
     if (ball_pos[1] > paddle1_pos) and (ball_pos[1] < (paddle1_pos + PAD_HEIGHT)): 
      ball_vel[0] = ball_vel[0] + (ball_vel[0] * (-2.1)) 
     else: 
      int_choice = 1 
      spawn_ball(direc) 
      score2 = score2 + 1 

    elif (ball_pos[0] + BALL_RADIUS) >= (WIDTH - PAD_WIDTH): 
     if (ball_pos[1] > paddle2_pos) and (ball_pos[1] < (paddle2_pos + PAD_HEIGHT)): 
      ball_vel[0] = ball_vel[0] + (ball_vel[0] * (-2.1)) 
     else: 
      int_choice = 0 
      spawn_ball(direc) 
      score1 = score1 + 1 
+0

'random.randint(0,1)'是'random.randrange(2)'的別名。考慮使用後者。 –

+1

爲什麼你甚至使用*兩個*全局意味着同樣的事情?而你的'left_or_right()'函數可以用一個列表來代替:'directions = ['LEFT','RIGHT']'和directions [int_choice]'會在每次需要文本時將整數轉換爲文本。 –

+0

你也傳遞給'spawn_ball()'的方向,然後*調用'left_or_right()'。爲什麼要通過這個方向,然後調用一個函數來重新設置它?該函數也會返回方向,但您無處處忽略返回值。 –

回答

4

您傳入的舊的的值爲direc,之後才調用left_or_right

說,你設置int_cohice爲1:

int_choice = 1 
spawn_ball(direc) # old value of `direc`, nothing changed this yet 

然後在spawn_ball()

def spawn_ball(direction): 
    left_or_right() 

所以direction被設置值,但left_or_right()其設置爲值,然後完全忽略spawn_ball()。整個功能使用direction

快速修復是使用返回值left_or_right();或使用全球的direc。因爲無論是在全局工作中,處於direc路過這裏沒有一點:

int_choice = 1 
spawn_ball() # don't pass anything in 

def spawn_ball(): 
    direction = left_or_right() 

然而,更好的辦法是總是傳球的方向,並徹底清除(雙)全局。

只是傳遞一個號碼,你可以給一些有象徵意義的名字:

LEFT, RIGHT = 0, 1 # symbolic names for direction 

def spawn_ball(direction): 
    ball_pos = [WIDTH/2, HEIGHT/2] 
    if direction == LEFT: # using the global symbolic name 
     return ball_pos, [ 
      random.randrange(12, 25)*(-0.1), 
      random.randrange(6, 19)*(-0.1)] 
    else: # naturally the other option is going to be RIGHT 
     return ball_pos, [ 
      random.randrange(12, 25)*(0.1) 
      random.randrange(6, 19)*(-0.1)] 

注意函數返回球的位置和速度;

ball_pos, ball_vel = spawn_ball(direction) 

也許draw功能還是將它們視爲全局,但是這不再是spawn_ball()功能的關心至少是:當你調用函數存儲結果。

現在你需要做的是建立一個本地變量要麼LEFTRIGHT產卵球和變量傳遞到函數。

1

你的問題,因爲你在你的代碼錯誤的時間更新變量。我們來看一個遊戲結束後會發生什麼的例子。

int_choice = 0 
spawn_ball(direc) 

您設置int_choice爲0,然後調用spawn_ball(直銷),但直銷是方向 - 這還沒有發生變化,只是int_choice了。所以現在direc已經綁定到你的spawn_ball函數中的「方向」變量。即使spawn_ball立即調用left_or_right(),那麼只會更新direc,而不會指向,這意味着spawn_ball將繼續與它最初傳入的方向相同,而不管對left_or_right的調用如何。

快速的解決辦法是說

def spawn_ball(direction): 
    direction = left_or_right() 

這將可能解決這個問題。不過,我建議你重構一下你的代碼 - 這是非常糟糕的風格。像你一樣傳遞全局變量很容易出現像這樣的錯誤 - 使用通過函數調用傳遞的局部變量是一個更好的選擇。